move occi, osm, rasterlite to non-core repo 84b0bfecb3
- refs #2980
This commit is contained in:
parent
c664394397
commit
2048be7b30
34 changed files with 0 additions and 4185 deletions
|
@ -110,14 +110,7 @@ PLUGINS = { # plugins with external dependencies
|
||||||
'pgraster': {'default':True,'path':None,'inc':'libpq-fe.h','lib':'pq','lang':'C'},
|
'pgraster': {'default':True,'path':None,'inc':'libpq-fe.h','lib':'pq','lang':'C'},
|
||||||
'gdal': {'default':True,'path':None,'inc':'gdal_priv.h','lib':'gdal','lang':'C++'},
|
'gdal': {'default':True,'path':None,'inc':'gdal_priv.h','lib':'gdal','lang':'C++'},
|
||||||
'ogr': {'default':True,'path':None,'inc':'ogrsf_frmts.h','lib':'gdal','lang':'C++'},
|
'ogr': {'default':True,'path':None,'inc':'ogrsf_frmts.h','lib':'gdal','lang':'C++'},
|
||||||
# configured with custom paths, hence 'path': PREFIX/INCLUDES/LIBS
|
|
||||||
'occi': {'default':False,'path':'OCCI','inc':'occi.h','lib':'clntsh','lang':'C++'},
|
|
||||||
'sqlite': {'default':True,'path':'SQLITE','inc':'sqlite3.h','lib':'sqlite3','lang':'C'},
|
'sqlite': {'default':True,'path':'SQLITE','inc':'sqlite3.h','lib':'sqlite3','lang':'C'},
|
||||||
'rasterlite': {'default':False,'path':'RASTERLITE','inc':['sqlite3.h','rasterlite.h'],'lib':'rasterlite','lang':'C'},
|
|
||||||
|
|
||||||
# todo: osm plugin does also depend on libxml2 (but there is a separate check for that)
|
|
||||||
'osm': {'default':False,'path':None,'inc':None,'lib':None,'lang':'C'},
|
|
||||||
|
|
||||||
# plugins without external dependencies requiring CheckLibWithHeader...
|
# plugins without external dependencies requiring CheckLibWithHeader...
|
||||||
'shape': {'default':True,'path':None,'inc':None,'lib':None,'lang':'C++'},
|
'shape': {'default':True,'path':None,'inc':None,'lib':None,'lang':'C++'},
|
||||||
'csv': {'default':True,'path':None,'inc':None,'lib':None,'lang':'C++'},
|
'csv': {'default':True,'path':None,'inc':None,'lib':None,'lang':'C++'},
|
||||||
|
|
|
@ -1,12 +0,0 @@
|
||||||
#
|
|
||||||
# To regenerate C++ class declarations & implementations for the Spatial
|
|
||||||
# object types of your database you should execute OTT in your server !
|
|
||||||
#
|
|
||||||
|
|
||||||
echo "TYPE MDSYS.SDO_POINT_TYPE AS SDOPointType" > spatial_types.typ
|
|
||||||
echo "TYPE MDSYS.SDO_GEOMETRY AS SDOGeometry" >> spatial_types.typ
|
|
||||||
|
|
||||||
ott userid=scott/tiger attraccess=private intype=spatial_types.typ code=cpp \
|
|
||||||
cppfile=spatial_classeso.cpp hfile=spatial_classesh.h mapfile=spatial_classesm.cpp \
|
|
||||||
mapfunc=RegisterClasses
|
|
||||||
|
|
|
@ -1,74 +0,0 @@
|
||||||
#
|
|
||||||
# This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
#
|
|
||||||
# Copyright (C) 2015 Artem Pavlenko
|
|
||||||
#
|
|
||||||
# Mapnik is free software; you can redistribute it and/or
|
|
||||||
# modify it under the terms of the GNU Lesser General Public
|
|
||||||
# License as published by the Free Software Foundation; either
|
|
||||||
# version 2.1 of the License, or (at your option) any later version.
|
|
||||||
#
|
|
||||||
# This library is distributed in the hope that it will be useful,
|
|
||||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
# Lesser General Public License for more details.
|
|
||||||
#
|
|
||||||
# You should have received a copy of the GNU Lesser General Public
|
|
||||||
# License along with this library; if not, write to the Free Software
|
|
||||||
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
#
|
|
||||||
#
|
|
||||||
|
|
||||||
Import ('plugin_base')
|
|
||||||
Import ('env')
|
|
||||||
|
|
||||||
PLUGIN_NAME = 'occi'
|
|
||||||
|
|
||||||
plugin_env = plugin_base.Clone()
|
|
||||||
|
|
||||||
plugin_sources = Split(
|
|
||||||
"""
|
|
||||||
%(PLUGIN_NAME)s_types.cpp
|
|
||||||
%(PLUGIN_NAME)s_datasource.cpp
|
|
||||||
%(PLUGIN_NAME)s_featureset.cpp
|
|
||||||
spatial_classesm.cpp
|
|
||||||
spatial_classeso.cpp
|
|
||||||
""" % locals()
|
|
||||||
)
|
|
||||||
|
|
||||||
libraries = [ 'clntsh', 'occi' ]
|
|
||||||
libraries.append('boost_system%s' % env['BOOST_APPEND'])
|
|
||||||
libraries.append(env['ICU_LIB_NAME'])
|
|
||||||
|
|
||||||
if env['PLUGIN_LINKING'] == 'shared':
|
|
||||||
libraries.append(env['MAPNIK_NAME'])
|
|
||||||
|
|
||||||
# libocci.dylib, at least for 11.2 links to libstdc++
|
|
||||||
# so we defer symbol resolution to runtime in order to
|
|
||||||
# dodge linking errors like
|
|
||||||
# Undefined symbols for architecture x86_64:
|
|
||||||
# "std::string::_Rep::_M_destroy(std::allocator<char> const&)", referenced from:
|
|
||||||
# RegisterClasses(oracle::occi::Environment*) in spatial_classesm.os
|
|
||||||
|
|
||||||
if env['PLATFORM'] == 'Darwin':
|
|
||||||
plugin_env.Append(LINKFLAGS='-undefined dynamic_lookup')
|
|
||||||
|
|
||||||
TARGET = plugin_env.SharedLibrary('../%s' % PLUGIN_NAME,
|
|
||||||
SHLIBPREFIX='',
|
|
||||||
SHLIBSUFFIX='.input',
|
|
||||||
source=plugin_sources,
|
|
||||||
LIBS=libraries)
|
|
||||||
|
|
||||||
# if the plugin links to libmapnik ensure it is built first
|
|
||||||
Depends(TARGET, env.subst('../../../src/%s' % env['MAPNIK_LIB_NAME']))
|
|
||||||
|
|
||||||
if 'uninstall' not in COMMAND_LINE_TARGETS:
|
|
||||||
env.Install(env['MAPNIK_INPUT_PLUGINS_DEST'], TARGET)
|
|
||||||
env.Alias('install', env['MAPNIK_INPUT_PLUGINS_DEST'])
|
|
||||||
|
|
||||||
plugin_obj = {
|
|
||||||
'LIBS': libraries,
|
|
||||||
'SOURCES': plugin_sources,
|
|
||||||
}
|
|
||||||
|
|
||||||
Return('plugin_obj')
|
|
|
@ -1,641 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#include "occi_datasource.hpp"
|
|
||||||
#include "occi_featureset.hpp"
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/boolean.hpp>
|
|
||||||
#include <mapnik/sql_utils.hpp>
|
|
||||||
#include <mapnik/timer.hpp>
|
|
||||||
#include <mapnik/value_types.hpp>
|
|
||||||
|
|
||||||
// boost
|
|
||||||
#include <boost/algorithm/string.hpp>
|
|
||||||
#include <boost/tokenizer.hpp>
|
|
||||||
|
|
||||||
// stl
|
|
||||||
#include <string>
|
|
||||||
#include <algorithm>
|
|
||||||
#include <set>
|
|
||||||
#include <sstream>
|
|
||||||
#include <iomanip>
|
|
||||||
|
|
||||||
using mapnik::datasource;
|
|
||||||
using mapnik::parameters;
|
|
||||||
using mapnik::query;
|
|
||||||
using mapnik::featureset_ptr;
|
|
||||||
using mapnik::layer_descriptor;
|
|
||||||
using mapnik::attribute_descriptor;
|
|
||||||
using mapnik::datasource_exception;
|
|
||||||
using mapnik::box2d;
|
|
||||||
using mapnik::coord2d;
|
|
||||||
|
|
||||||
using oracle::occi::Environment;
|
|
||||||
using oracle::occi::Connection;
|
|
||||||
using oracle::occi::Statement;
|
|
||||||
using oracle::occi::ResultSet;
|
|
||||||
using oracle::occi::MetaData;
|
|
||||||
using oracle::occi::SQLException;
|
|
||||||
using oracle::occi::Type;
|
|
||||||
using oracle::occi::StatelessConnectionPool;
|
|
||||||
|
|
||||||
const double occi_datasource::FMAX = std::numeric_limits<double>::max();
|
|
||||||
const std::string occi_datasource::METADATA_TABLE = "USER_SDO_GEOM_METADATA";
|
|
||||||
|
|
||||||
DATASOURCE_PLUGIN(occi_datasource)
|
|
||||||
|
|
||||||
occi_datasource::occi_datasource(parameters const& params)
|
|
||||||
: datasource (params),
|
|
||||||
type_(datasource::Vector),
|
|
||||||
fields_(*params.get<std::string>("fields", "*")),
|
|
||||||
geometry_field_(*params.get<std::string>("geometry_field", "")),
|
|
||||||
srid_initialized_(false),
|
|
||||||
extent_initialized_(false),
|
|
||||||
bbox_token_("!bbox!"),
|
|
||||||
scale_denom_token_("!scale_denominator!"),
|
|
||||||
pixel_width_token_("!pixel_width!"),
|
|
||||||
pixel_height_token_("!pixel_height!"),
|
|
||||||
desc_(occi_datasource::name(), *params.get<std::string>("encoding", "utf-8")),
|
|
||||||
use_wkb_(*params.get<mapnik::boolean_type>("use_wkb", false)),
|
|
||||||
row_limit_(*params.get<mapnik::value_integer>("row_limit", 0)),
|
|
||||||
row_prefetch_(*params.get<mapnik::value_integer>("row_prefetch", 100)),
|
|
||||||
pool_(0),
|
|
||||||
conn_(0)
|
|
||||||
{
|
|
||||||
#ifdef MAPNIK_STATS
|
|
||||||
mapnik::progress_timer __stats__(std::clog, "occi_datasource::init");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if (! params.get<std::string>("user")) throw datasource_exception("OCCI Plugin: no <user> specified");
|
|
||||||
if (! params.get<std::string>("password")) throw datasource_exception("OCCI Plugin: no <password> specified");
|
|
||||||
if (! params.get<std::string>("host")) throw datasource_exception("OCCI Plugin: no <host> string specified");
|
|
||||||
|
|
||||||
boost::optional<std::string> table = params.get<std::string>("table");
|
|
||||||
if (! table)
|
|
||||||
{
|
|
||||||
throw datasource_exception("OCCI Plugin: no <table> parameter specified");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
table_ = *table;
|
|
||||||
}
|
|
||||||
estimate_extent_ = *params.get<mapnik::boolean_type>("estimate_extent",false);
|
|
||||||
use_spatial_index_ = *params.get<mapnik::boolean_type>("use_spatial_index",true);
|
|
||||||
use_connection_pool_ = *params.get<mapnik::boolean_type>("use_connection_pool",true);
|
|
||||||
|
|
||||||
boost::optional<std::string> ext = params.get<std::string>("extent");
|
|
||||||
if (ext) extent_initialized_ = extent_.from_string(*ext);
|
|
||||||
|
|
||||||
boost::optional<mapnik::value_integer> srid = params.get<mapnik::value_integer>("srid");
|
|
||||||
if (srid)
|
|
||||||
{
|
|
||||||
srid_ = *srid;
|
|
||||||
srid_initialized_ = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// connect to environment
|
|
||||||
if (use_connection_pool_)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
pool_ = occi_environment::instance().create_pool(
|
|
||||||
*params.get<std::string>("user"),
|
|
||||||
*params.get<std::string>("password"),
|
|
||||||
*params.get<std::string>("host"),
|
|
||||||
*params.get<mapnik::value_integer>("max_size", 5),
|
|
||||||
*params.get<mapnik::value_integer>("initial_size", 1),
|
|
||||||
1);
|
|
||||||
}
|
|
||||||
catch (SQLException& ex)
|
|
||||||
{
|
|
||||||
throw datasource_exception("OCCI Plugin: " + ex.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
conn_ = occi_environment::instance().create_connection(
|
|
||||||
*params.get<std::string>("user"),
|
|
||||||
*params.get<std::string>("password"),
|
|
||||||
*params.get<std::string>("host"));
|
|
||||||
}
|
|
||||||
catch (SQLException& ex)
|
|
||||||
{
|
|
||||||
throw datasource_exception("OCCI Plugin: " + ex.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// extract real table name
|
|
||||||
table_name_ = mapnik::sql_utils::table_from_sql(table_);
|
|
||||||
|
|
||||||
// get SRID and/or GEOMETRY_FIELD from metadata table only if we need to
|
|
||||||
if (! srid_initialized_ || geometry_field_ == "")
|
|
||||||
{
|
|
||||||
#ifdef MAPNIK_STATS
|
|
||||||
mapnik::progress_timer __stats__(std::clog, "occi_datasource::get_srid_and_geometry_field");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
std::ostringstream s;
|
|
||||||
s << "SELECT srid, column_name FROM " << METADATA_TABLE << " WHERE";
|
|
||||||
s << " LOWER(table_name) = LOWER('" << table_name_ << "')";
|
|
||||||
|
|
||||||
if (geometry_field_ != "")
|
|
||||||
{
|
|
||||||
s << " AND LOWER(column_name) = LOWER('" << geometry_field_ << "')";
|
|
||||||
}
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_datasource: " << s.str();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
occi_connection_ptr conn;
|
|
||||||
if (use_connection_pool_) conn.set_pool(pool_);
|
|
||||||
else conn.set_connection(conn_, false);
|
|
||||||
|
|
||||||
ResultSet* rs = conn.execute_query(s.str());
|
|
||||||
if (rs && rs->next ())
|
|
||||||
{
|
|
||||||
if (! srid_initialized_)
|
|
||||||
{
|
|
||||||
srid_ = rs->getInt(1);
|
|
||||||
srid_initialized_ = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (geometry_field_ == "")
|
|
||||||
{
|
|
||||||
geometry_field_ = rs->getString(2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (SQLException& ex)
|
|
||||||
{
|
|
||||||
throw datasource_exception("OCCI Plugin: " + ex.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// get columns description
|
|
||||||
{
|
|
||||||
#ifdef MAPNIK_STATS
|
|
||||||
mapnik::progress_timer __stats__(std::clog, "occi_datasource::get_column_description");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
std::ostringstream s;
|
|
||||||
s << "SELECT " << fields_ << " FROM (" << table_name_ << ") WHERE ROWNUM < 1";
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_datasource: " << s.str();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
occi_connection_ptr conn;
|
|
||||||
if (use_connection_pool_) conn.set_pool(pool_);
|
|
||||||
else conn.set_connection(conn_, false);
|
|
||||||
|
|
||||||
ResultSet* rs = conn.execute_query(s.str());
|
|
||||||
if (rs)
|
|
||||||
{
|
|
||||||
std::vector<MetaData> listOfColumns = rs->getColumnListMetaData();
|
|
||||||
|
|
||||||
for (unsigned int i = 0; i < listOfColumns.size(); ++i)
|
|
||||||
{
|
|
||||||
MetaData columnObj = listOfColumns[i];
|
|
||||||
|
|
||||||
std::string fld_name = columnObj.getString(MetaData::ATTR_NAME);
|
|
||||||
int type_oid = columnObj.getInt(MetaData::ATTR_DATA_TYPE);
|
|
||||||
|
|
||||||
/*
|
|
||||||
int type_code = columnObj.getInt(MetaData::ATTR_TYPECODE);
|
|
||||||
if (type_code == OCCI_TYPECODE_OBJECT)
|
|
||||||
{
|
|
||||||
desc_.add_descriptor(attribute_descriptor(fld_name,mapnik::Object));
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
switch (type_oid)
|
|
||||||
{
|
|
||||||
case oracle::occi::OCCIBOOL:
|
|
||||||
desc_.add_descriptor(attribute_descriptor(fld_name,mapnik::Boolean));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCIINT:
|
|
||||||
case oracle::occi::OCCIUNSIGNED_INT:
|
|
||||||
desc_.add_descriptor(attribute_descriptor(fld_name,mapnik::Integer));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCIFLOAT:
|
|
||||||
case oracle::occi::OCCIBFLOAT:
|
|
||||||
case oracle::occi::OCCIDOUBLE:
|
|
||||||
case oracle::occi::OCCIBDOUBLE:
|
|
||||||
case oracle::occi::OCCINUMBER:
|
|
||||||
case oracle::occi::OCCI_SQLT_NUM:
|
|
||||||
desc_.add_descriptor(attribute_descriptor(fld_name,mapnik::Double));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCICHAR:
|
|
||||||
case oracle::occi::OCCISTRING:
|
|
||||||
case oracle::occi::OCCI_SQLT_AFC:
|
|
||||||
case oracle::occi::OCCI_SQLT_AVC:
|
|
||||||
case oracle::occi::OCCI_SQLT_CHR:
|
|
||||||
case oracle::occi::OCCI_SQLT_LNG:
|
|
||||||
case oracle::occi::OCCI_SQLT_LVC:
|
|
||||||
case oracle::occi::OCCI_SQLT_STR:
|
|
||||||
case oracle::occi::OCCI_SQLT_VCS:
|
|
||||||
case oracle::occi::OCCI_SQLT_VNU:
|
|
||||||
case oracle::occi::OCCI_SQLT_VBI:
|
|
||||||
case oracle::occi::OCCI_SQLT_VST:
|
|
||||||
case oracle::occi::OCCIROWID:
|
|
||||||
case oracle::occi::OCCI_SQLT_RDD:
|
|
||||||
case oracle::occi::OCCI_SQLT_RID:
|
|
||||||
case oracle::occi::OCCIDATE:
|
|
||||||
case oracle::occi::OCCI_SQLT_DAT:
|
|
||||||
case oracle::occi::OCCI_SQLT_DATE:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIME:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIME_TZ:
|
|
||||||
case oracle::occi::OCCITIMESTAMP:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP_LTZ:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP_TZ:
|
|
||||||
desc_.add_descriptor(attribute_descriptor(fld_name,mapnik::String));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCIINTERVALDS:
|
|
||||||
case oracle::occi::OCCIINTERVALYM:
|
|
||||||
case oracle::occi::OCCI_SQLT_INTERVAL_YM:
|
|
||||||
case oracle::occi::OCCI_SQLT_INTERVAL_DS:
|
|
||||||
case oracle::occi::OCCIANYDATA:
|
|
||||||
case oracle::occi::OCCIBLOB:
|
|
||||||
case oracle::occi::OCCIBFILE:
|
|
||||||
case oracle::occi::OCCIBYTES:
|
|
||||||
case oracle::occi::OCCICLOB:
|
|
||||||
case oracle::occi::OCCIVECTOR:
|
|
||||||
case oracle::occi::OCCIMETADATA:
|
|
||||||
case oracle::occi::OCCIPOBJECT:
|
|
||||||
case oracle::occi::OCCIREF:
|
|
||||||
case oracle::occi::OCCIREFANY:
|
|
||||||
case oracle::occi::OCCISTREAM:
|
|
||||||
case oracle::occi::OCCICURSOR:
|
|
||||||
case oracle::occi::OCCI_SQLT_FILE:
|
|
||||||
case oracle::occi::OCCI_SQLT_CFILE:
|
|
||||||
case oracle::occi::OCCI_SQLT_REF:
|
|
||||||
case oracle::occi::OCCI_SQLT_CLOB:
|
|
||||||
case oracle::occi::OCCI_SQLT_BLOB:
|
|
||||||
case oracle::occi::OCCI_SQLT_RSET:
|
|
||||||
MAPNIK_LOG_WARN(occi) << "occi_datasource: Unsupported datatype "
|
|
||||||
<< occi_enums::resolve_datatype(type_oid)
|
|
||||||
<< " (type_oid=" << type_oid << ")";
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
MAPNIK_LOG_WARN(occi) << "occi_datasource: Unknown datatype "
|
|
||||||
<< "(type_oid=" << type_oid << ")";
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (SQLException& ex)
|
|
||||||
{
|
|
||||||
throw datasource_exception(ex.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
occi_datasource::~occi_datasource()
|
|
||||||
{
|
|
||||||
if (use_connection_pool_)
|
|
||||||
{
|
|
||||||
if (pool_ != 0)
|
|
||||||
{
|
|
||||||
occi_environment::instance().destroy_pool(pool_);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (conn_ != 0)
|
|
||||||
{
|
|
||||||
occi_environment::instance().destroy_connection(conn_);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const char * occi_datasource::name()
|
|
||||||
{
|
|
||||||
return "occi";
|
|
||||||
}
|
|
||||||
|
|
||||||
mapnik::datasource::datasource_t occi_datasource::type() const
|
|
||||||
{
|
|
||||||
return type_;
|
|
||||||
}
|
|
||||||
|
|
||||||
box2d<double> occi_datasource::envelope() const
|
|
||||||
{
|
|
||||||
if (extent_initialized_) return extent_;
|
|
||||||
|
|
||||||
double lox = 0.0, loy = 0.0, hix = 0.0, hiy = 0.0;
|
|
||||||
|
|
||||||
|
|
||||||
if (estimate_extent_)
|
|
||||||
{
|
|
||||||
#ifdef MAPNIK_STATS
|
|
||||||
mapnik::progress_timer __stats__(std::clog, "occi_datasource::envelope(estimate_extent)");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
std::ostringstream s;
|
|
||||||
s << "SELECT MIN(c.x), MIN(c.y), MAX(c.x), MAX(c.y) FROM ";
|
|
||||||
s << " (SELECT SDO_AGGR_MBR(" << geometry_field_ << ") shape FROM " << table_ << ") a, ";
|
|
||||||
s << " TABLE(SDO_UTIL.GETVERTICES(a.shape)) c";
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_datasource: " << s.str();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
occi_connection_ptr conn;
|
|
||||||
if (use_connection_pool_) conn.set_pool(pool_);
|
|
||||||
else conn.set_connection(conn_, false);
|
|
||||||
|
|
||||||
ResultSet* rs = conn.execute_query(s.str());
|
|
||||||
if (rs && rs->next())
|
|
||||||
{
|
|
||||||
lox = rs->getDouble(1);
|
|
||||||
loy = rs->getDouble(2);
|
|
||||||
hix = rs->getDouble(3);
|
|
||||||
hiy = rs->getDouble(4);
|
|
||||||
extent_.init(lox, loy, hix, hiy);
|
|
||||||
extent_initialized_ = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (SQLException& ex)
|
|
||||||
{
|
|
||||||
throw datasource_exception("OCCI Plugin: " + ex.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (use_spatial_index_)
|
|
||||||
{
|
|
||||||
#ifdef MAPNIK_STATS
|
|
||||||
mapnik::progress_timer __stats__(std::clog, "occi_datasource::envelope(use_spatial_index)");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
std::ostringstream s;
|
|
||||||
s << "SELECT dim.sdo_lb, dim.sdo_ub FROM ";
|
|
||||||
s << METADATA_TABLE << " m, TABLE(m.diminfo) dim ";
|
|
||||||
s << " WHERE LOWER(m.table_name) = LOWER('" << table_name_ << "') AND dim.sdo_dimname = 'X'";
|
|
||||||
s << " UNION ";
|
|
||||||
s << "SELECT dim.sdo_lb, dim.sdo_ub FROM ";
|
|
||||||
s << METADATA_TABLE << " m, TABLE(m.diminfo) dim ";
|
|
||||||
s << " WHERE LOWER(m.table_name) = LOWER('" << table_name_ << "') AND dim.sdo_dimname = 'Y'";
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_datasource: " << s.str();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
occi_connection_ptr conn;
|
|
||||||
if (use_connection_pool_) conn.set_pool(pool_);
|
|
||||||
else conn.set_connection(conn_, false);
|
|
||||||
|
|
||||||
ResultSet* rs = conn.execute_query(s.str());
|
|
||||||
if (rs)
|
|
||||||
{
|
|
||||||
if (rs->next())
|
|
||||||
{
|
|
||||||
lox = rs->getDouble(1);
|
|
||||||
hix = rs->getDouble(2);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (rs->next())
|
|
||||||
{
|
|
||||||
loy = rs->getDouble(1);
|
|
||||||
hiy = rs->getDouble(2);
|
|
||||||
}
|
|
||||||
extent_.init(lox, loy, hix, hiy);
|
|
||||||
extent_initialized_ = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (SQLException& ex)
|
|
||||||
{
|
|
||||||
throw datasource_exception("OCCI Plugin: " + ex.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (! extent_initialized_)
|
|
||||||
{
|
|
||||||
throw datasource_exception("OCCI Plugin: unable to determine the extent of a <occi> table");
|
|
||||||
}
|
|
||||||
|
|
||||||
return extent_;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
boost::optional<mapnik::datasource_geometry_t> occi_datasource::get_geometry_type() const
|
|
||||||
{
|
|
||||||
return boost::optional<mapnik::datasource_geometry_t>();
|
|
||||||
}
|
|
||||||
|
|
||||||
layer_descriptor occi_datasource::get_descriptor() const
|
|
||||||
{
|
|
||||||
return desc_;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string occi_datasource::sql_bbox(box2d<double> const& env) const
|
|
||||||
{
|
|
||||||
std::ostringstream b;
|
|
||||||
b << std::setprecision(16);
|
|
||||||
b << "MDSYS.SDO_GEOMETRY(" << SDO_GTYPE_2DPOLYGON << "," << srid_ << ",NULL,";
|
|
||||||
b << " MDSYS.SDO_ELEM_INFO_ARRAY(1," << SDO_ETYPE_POLYGON << "," << SDO_INTERPRETATION_RECTANGLE << "),";
|
|
||||||
b << " MDSYS.SDO_ORDINATE_ARRAY(";
|
|
||||||
b << env.minx() << "," << env.miny() << ", ";
|
|
||||||
b << env.maxx() << "," << env.maxy() << "))";
|
|
||||||
return b.str();
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string occi_datasource::populate_tokens(std::string const& sql, double scale_denom, box2d<double> const& env, double pixel_width, double pixel_height) const
|
|
||||||
{
|
|
||||||
std::string populated_sql = sql;
|
|
||||||
|
|
||||||
if (boost::algorithm::icontains(populated_sql, scale_denom_token_))
|
|
||||||
{
|
|
||||||
std::ostringstream ss;
|
|
||||||
ss << scale_denom;
|
|
||||||
boost::algorithm::replace_all(populated_sql, scale_denom_token_, ss.str());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (boost::algorithm::icontains(sql, pixel_width_token_))
|
|
||||||
{
|
|
||||||
std::ostringstream ss;
|
|
||||||
ss << pixel_width;
|
|
||||||
boost::algorithm::replace_all(populated_sql, pixel_width_token_, ss.str());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (boost::algorithm::icontains(sql, pixel_height_token_))
|
|
||||||
{
|
|
||||||
std::ostringstream ss;
|
|
||||||
ss << pixel_height;
|
|
||||||
boost::algorithm::replace_all(populated_sql, pixel_height_token_, ss.str());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (boost::algorithm::icontains(populated_sql, bbox_token_))
|
|
||||||
{
|
|
||||||
boost::algorithm::replace_all(populated_sql, bbox_token_, sql_bbox(env));
|
|
||||||
}
|
|
||||||
|
|
||||||
return populated_sql;
|
|
||||||
}
|
|
||||||
|
|
||||||
featureset_ptr occi_datasource::features(query const& q) const
|
|
||||||
{
|
|
||||||
#ifdef MAPNIK_STATS
|
|
||||||
mapnik::progress_timer __stats__(std::clog, "occi_datasource::features");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
box2d<double> const& box = q.get_bbox();
|
|
||||||
const double px_gw = 1.0 / std::get<0>(q.resolution());
|
|
||||||
const double px_gh = 1.0 / std::get<1>(q.resolution());
|
|
||||||
const double scale_denom = q.scale_denominator();
|
|
||||||
|
|
||||||
std::ostringstream s;
|
|
||||||
s << "SELECT ";
|
|
||||||
if (use_wkb_)
|
|
||||||
{
|
|
||||||
s << "SDO_UTIL.TO_WKBGEOMETRY(" << geometry_field_ << ")";
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
s << geometry_field_;
|
|
||||||
}
|
|
||||||
std::set<std::string> const& props = q.property_names();
|
|
||||||
std::set<std::string>::const_iterator pos = props.begin();
|
|
||||||
std::set<std::string>::const_iterator end = props.end();
|
|
||||||
mapnik::context_ptr ctx = std::make_shared<mapnik::context_type>();
|
|
||||||
for (; pos != end; ++pos)
|
|
||||||
{
|
|
||||||
s << ", " << *pos;
|
|
||||||
ctx->push(*pos);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string query = populate_tokens(table_, scale_denom, box, px_gw, px_gh);
|
|
||||||
|
|
||||||
if (use_spatial_index_)
|
|
||||||
{
|
|
||||||
std::ostringstream spatial_sql;
|
|
||||||
spatial_sql << " WHERE SDO_FILTER(";
|
|
||||||
spatial_sql << geometry_field_ << "," << sql_bbox(box);
|
|
||||||
spatial_sql << ", 'querytype = WINDOW') = 'TRUE'";
|
|
||||||
|
|
||||||
if (boost::algorithm::ifind_first(query, "WHERE"))
|
|
||||||
{
|
|
||||||
boost::algorithm::ireplace_first(query, "WHERE", spatial_sql.str() + " AND ");
|
|
||||||
}
|
|
||||||
else if (boost::algorithm::ifind_first(query, table_name_))
|
|
||||||
{
|
|
||||||
boost::algorithm::ireplace_first(query, table_name_, table_name_ + " " + spatial_sql.str());
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_WARN(occi) << "occi_datasource: cannot determine where to add the spatial filter declaration";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
s << " FROM " << query;
|
|
||||||
|
|
||||||
if (row_limit_ > 0)
|
|
||||||
{
|
|
||||||
s << " WHERE ROWNUM < " << row_limit_;
|
|
||||||
}
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_datasource: " << s.str();
|
|
||||||
|
|
||||||
return std::make_shared<occi_featureset>(pool_,
|
|
||||||
conn_,
|
|
||||||
ctx,
|
|
||||||
s.str(),
|
|
||||||
desc_.get_encoding(),
|
|
||||||
use_connection_pool_,
|
|
||||||
use_wkb_,
|
|
||||||
row_prefetch_);
|
|
||||||
}
|
|
||||||
|
|
||||||
featureset_ptr occi_datasource::features_at_point(coord2d const& pt, double tol) const
|
|
||||||
{
|
|
||||||
#ifdef MAPNIK_STATS
|
|
||||||
mapnik::progress_timer __stats__(std::clog, "occi_datasource::features_at_point");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
std::ostringstream s;
|
|
||||||
s << "SELECT ";
|
|
||||||
if (use_wkb_)
|
|
||||||
{
|
|
||||||
s << "SDO_UTIL.TO_WKBGEOMETRY(" << geometry_field_ << ")";
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
s << geometry_field_;
|
|
||||||
}
|
|
||||||
std::vector<attribute_descriptor>::const_iterator itr = desc_.get_descriptors().begin();
|
|
||||||
std::vector<attribute_descriptor>::const_iterator end = desc_.get_descriptors().end();
|
|
||||||
mapnik::context_ptr ctx = std::make_shared<mapnik::context_type>();
|
|
||||||
while (itr != end)
|
|
||||||
{
|
|
||||||
s << ", " << itr->get_name();
|
|
||||||
ctx->push(itr->get_name());
|
|
||||||
++itr;
|
|
||||||
}
|
|
||||||
|
|
||||||
box2d<double> box(pt.x - tol, pt.y - tol, pt.x + tol, pt.y + tol);
|
|
||||||
std::string query = populate_tokens(table_, FMAX, box, 0, 0);
|
|
||||||
|
|
||||||
if (use_spatial_index_)
|
|
||||||
{
|
|
||||||
std::ostringstream spatial_sql;
|
|
||||||
spatial_sql << " WHERE SDO_FILTER(";
|
|
||||||
spatial_sql << geometry_field_ << "," << sql_bbox(box);
|
|
||||||
spatial_sql << ", 'querytype = WINDOW') = 'TRUE'";
|
|
||||||
|
|
||||||
if (boost::algorithm::ifind_first(query, "WHERE"))
|
|
||||||
{
|
|
||||||
boost::algorithm::ireplace_first(query, "WHERE", spatial_sql.str() + " AND ");
|
|
||||||
}
|
|
||||||
else if (boost::algorithm::ifind_first(query, table_name_))
|
|
||||||
{
|
|
||||||
boost::algorithm::ireplace_first(query, table_name_, table_name_ + " " + spatial_sql.str());
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_WARN(occi) << "occi_datasource: Cannot determine where to add the spatial filter declaration";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
s << " FROM " << query;
|
|
||||||
|
|
||||||
if (row_limit_ > 0)
|
|
||||||
{
|
|
||||||
s << " WHERE ROWNUM < " << row_limit_;
|
|
||||||
}
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_datasource: " << s.str();
|
|
||||||
|
|
||||||
return std::make_shared<occi_featureset>(pool_,
|
|
||||||
conn_,
|
|
||||||
ctx,
|
|
||||||
s.str(),
|
|
||||||
desc_.get_encoding(),
|
|
||||||
use_connection_pool_,
|
|
||||||
use_wkb_,
|
|
||||||
row_prefetch_);
|
|
||||||
}
|
|
|
@ -1,95 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OCCI_DATASOURCE_HPP
|
|
||||||
#define OCCI_DATASOURCE_HPP
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/datasource.hpp>
|
|
||||||
#include <mapnik/params.hpp>
|
|
||||||
#include <mapnik/query.hpp>
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/box2d.hpp>
|
|
||||||
#include <mapnik/coord.hpp>
|
|
||||||
#include <mapnik/feature_layer_desc.hpp>
|
|
||||||
#include <mapnik/value_types.hpp>
|
|
||||||
|
|
||||||
// boost
|
|
||||||
#include <boost/optional.hpp>
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
// stl
|
|
||||||
#include <vector>
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
// oci
|
|
||||||
#include "occi_types.hpp"
|
|
||||||
|
|
||||||
class occi_datasource : public mapnik::datasource
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
occi_datasource(mapnik::parameters const& params);
|
|
||||||
virtual ~occi_datasource ();
|
|
||||||
mapnik::datasource::datasource_t type() const;
|
|
||||||
static const char * name();
|
|
||||||
mapnik::featureset_ptr features(mapnik::query const& q) const;
|
|
||||||
mapnik::featureset_ptr features_at_point(mapnik::coord2d const& pt, double tol = 0) const;
|
|
||||||
mapnik::box2d<double> envelope() const;
|
|
||||||
boost::optional<mapnik::datasource_geometry_t> get_geometry_type() const;
|
|
||||||
mapnik::layer_descriptor get_descriptor() const;
|
|
||||||
|
|
||||||
private:
|
|
||||||
std::string sql_bbox(mapnik::box2d<double> const& env) const;
|
|
||||||
std::string populate_tokens(std::string const& sql,
|
|
||||||
double scale_denom,
|
|
||||||
mapnik::box2d<double> const& env,
|
|
||||||
double pixel_width,
|
|
||||||
double pixel_height) const;
|
|
||||||
|
|
||||||
static const std::string METADATA_TABLE;
|
|
||||||
static const double FMAX;
|
|
||||||
|
|
||||||
mapnik::datasource::datasource_t type_;
|
|
||||||
std::string table_;
|
|
||||||
std::string table_name_;
|
|
||||||
std::string fields_;
|
|
||||||
std::string geometry_field_;
|
|
||||||
int srid_;
|
|
||||||
bool srid_initialized_;
|
|
||||||
mutable bool extent_initialized_;
|
|
||||||
mutable mapnik::box2d<double> extent_;
|
|
||||||
const std::string bbox_token_;
|
|
||||||
const std::string scale_denom_token_;
|
|
||||||
const std::string pixel_width_token_;
|
|
||||||
const std::string pixel_height_token_;
|
|
||||||
mapnik::layer_descriptor desc_;
|
|
||||||
bool use_wkb_;
|
|
||||||
mapnik::value_integer row_limit_;
|
|
||||||
int row_prefetch_;
|
|
||||||
oracle::occi::StatelessConnectionPool* pool_;
|
|
||||||
oracle::occi::Connection* conn_;
|
|
||||||
bool use_connection_pool_;
|
|
||||||
bool use_spatial_index_;
|
|
||||||
bool estimate_extent_;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OCCI_DATASOURCE_HPP
|
|
|
@ -1,516 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/global.hpp>
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/box2d.hpp>
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/feature_layer_desc.hpp>
|
|
||||||
#include <mapnik/wkb.hpp>
|
|
||||||
#include <mapnik/unicode.hpp>
|
|
||||||
#include <mapnik/value_types.hpp>
|
|
||||||
#include <mapnik/feature_factory.hpp>
|
|
||||||
#include <mapnik/make_unique.hpp>
|
|
||||||
|
|
||||||
// ogr
|
|
||||||
#include "occi_featureset.hpp"
|
|
||||||
|
|
||||||
using mapnik::query;
|
|
||||||
using mapnik::box2d;
|
|
||||||
using mapnik::feature_ptr;
|
|
||||||
using mapnik::geometry_type;
|
|
||||||
using mapnik::geometry_utils;
|
|
||||||
using mapnik::transcoder;
|
|
||||||
using mapnik::datasource_exception;
|
|
||||||
using mapnik::feature_factory;
|
|
||||||
|
|
||||||
using oracle::occi::Connection;
|
|
||||||
using oracle::occi::Statement;
|
|
||||||
using oracle::occi::ResultSet;
|
|
||||||
using oracle::occi::StatelessConnectionPool;
|
|
||||||
using oracle::occi::MetaData;
|
|
||||||
using oracle::occi::SQLException;
|
|
||||||
using oracle::occi::Type;
|
|
||||||
using oracle::occi::Number;
|
|
||||||
using oracle::occi::Blob;
|
|
||||||
|
|
||||||
occi_featureset::occi_featureset(StatelessConnectionPool* pool,
|
|
||||||
Connection* conn,
|
|
||||||
mapnik::context_ptr const& ctx,
|
|
||||||
std::string const& sqlstring,
|
|
||||||
std::string const& encoding,
|
|
||||||
bool use_connection_pool,
|
|
||||||
bool use_wkb,
|
|
||||||
unsigned prefetch_rows)
|
|
||||||
: rs_(nullptr),
|
|
||||||
tr_(new transcoder(encoding)),
|
|
||||||
feature_id_(1),
|
|
||||||
ctx_(ctx),
|
|
||||||
use_wkb_(use_wkb)
|
|
||||||
{
|
|
||||||
if (use_connection_pool)
|
|
||||||
{
|
|
||||||
conn_.set_pool(pool);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
conn_.set_connection(conn, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
rs_ = conn_.execute_query(sqlstring, prefetch_rows);
|
|
||||||
}
|
|
||||||
catch (SQLException &ex)
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_ERROR(occi) << "OCCI Plugin: error processing " << sqlstring << " : " << ex.getMessage();
|
|
||||||
|
|
||||||
rs_ = nullptr;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
occi_featureset::~occi_featureset()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
feature_ptr occi_featureset::next()
|
|
||||||
{
|
|
||||||
while (rs_ != nullptr && rs_->next() == oracle::occi::ResultSet::DATA_AVAILABLE)
|
|
||||||
{
|
|
||||||
feature_ptr feature(feature_factory::create(ctx_, feature_id_));
|
|
||||||
|
|
||||||
if (use_wkb_)
|
|
||||||
{
|
|
||||||
Blob blob = rs_->getBlob(1);
|
|
||||||
blob.open(oracle::occi::OCCI_LOB_READONLY);
|
|
||||||
|
|
||||||
unsigned int size = blob.length();
|
|
||||||
if (buffer_.size() < size)
|
|
||||||
{
|
|
||||||
buffer_.resize(size);
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::Stream* instream = blob.getStream(1, 0);
|
|
||||||
instream->readBuffer(buffer_.data(), size);
|
|
||||||
blob.closeStream(instream);
|
|
||||||
blob.close();
|
|
||||||
|
|
||||||
if (! geometry_utils::from_wkb(feature->paths(), buffer_.data(), size))
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
const std::unique_ptr<SDOGeometry> geom(dynamic_cast<SDOGeometry*>(rs_->getObject(1)));
|
|
||||||
if (geom.get())
|
|
||||||
{
|
|
||||||
convert_geometry(geom.get(), feature);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
std::vector<MetaData> listOfColumns = rs_->getColumnListMetaData();
|
|
||||||
|
|
||||||
for (unsigned int i = 1; i < listOfColumns.size(); ++i)
|
|
||||||
{
|
|
||||||
MetaData columnObj = listOfColumns[i];
|
|
||||||
|
|
||||||
std::string fld_name = columnObj.getString(MetaData::ATTR_NAME);
|
|
||||||
int type_oid = columnObj.getInt(MetaData::ATTR_DATA_TYPE);
|
|
||||||
|
|
||||||
/*
|
|
||||||
int type_code = columnObj.getInt(MetaData::ATTR_TYPECODE);
|
|
||||||
if (type_code == OCCI_TYPECODE_OBJECT)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
switch (type_oid)
|
|
||||||
{
|
|
||||||
case oracle::occi::OCCIBOOL:
|
|
||||||
feature->put(fld_name, (rs_->getInt(i + 1) != 0));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCIINT:
|
|
||||||
case oracle::occi::OCCIUNSIGNED_INT:
|
|
||||||
feature->put(fld_name, static_cast<mapnik::value_integer>(rs_->getInt(i + 1)));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCIFLOAT:
|
|
||||||
case oracle::occi::OCCIBFLOAT:
|
|
||||||
feature->put(fld_name, (double)rs_->getFloat(i + 1));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCIDOUBLE:
|
|
||||||
case oracle::occi::OCCIBDOUBLE:
|
|
||||||
case oracle::occi::OCCINUMBER:
|
|
||||||
case oracle::occi::OCCI_SQLT_NUM:
|
|
||||||
feature->put(fld_name, rs_->getDouble(i + 1));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCICHAR:
|
|
||||||
case oracle::occi::OCCISTRING:
|
|
||||||
case oracle::occi::OCCI_SQLT_AFC:
|
|
||||||
case oracle::occi::OCCI_SQLT_AVC:
|
|
||||||
case oracle::occi::OCCI_SQLT_CHR:
|
|
||||||
case oracle::occi::OCCI_SQLT_LNG:
|
|
||||||
case oracle::occi::OCCI_SQLT_LVC:
|
|
||||||
case oracle::occi::OCCI_SQLT_STR:
|
|
||||||
case oracle::occi::OCCI_SQLT_VCS:
|
|
||||||
case oracle::occi::OCCI_SQLT_VNU:
|
|
||||||
case oracle::occi::OCCI_SQLT_VBI:
|
|
||||||
case oracle::occi::OCCI_SQLT_VST:
|
|
||||||
case oracle::occi::OCCIROWID:
|
|
||||||
case oracle::occi::OCCI_SQLT_RDD:
|
|
||||||
case oracle::occi::OCCI_SQLT_RID:
|
|
||||||
case oracle::occi::OCCIDATE:
|
|
||||||
case oracle::occi::OCCI_SQLT_DAT:
|
|
||||||
case oracle::occi::OCCI_SQLT_DATE:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIME:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIME_TZ:
|
|
||||||
case oracle::occi::OCCITIMESTAMP:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP_LTZ:
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP_TZ:
|
|
||||||
feature->put(fld_name, static_cast<mapnik::value_unicode_string>(tr_->transcode(rs_->getString(i + 1).c_str())));
|
|
||||||
break;
|
|
||||||
case oracle::occi::OCCIINTERVALDS:
|
|
||||||
case oracle::occi::OCCIINTERVALYM:
|
|
||||||
case oracle::occi::OCCI_SQLT_INTERVAL_YM:
|
|
||||||
case oracle::occi::OCCI_SQLT_INTERVAL_DS:
|
|
||||||
case oracle::occi::OCCIANYDATA:
|
|
||||||
case oracle::occi::OCCIBLOB:
|
|
||||||
case oracle::occi::OCCIBFILE:
|
|
||||||
case oracle::occi::OCCIBYTES:
|
|
||||||
case oracle::occi::OCCICLOB:
|
|
||||||
case oracle::occi::OCCIVECTOR:
|
|
||||||
case oracle::occi::OCCIMETADATA:
|
|
||||||
case oracle::occi::OCCIPOBJECT:
|
|
||||||
case oracle::occi::OCCIREF:
|
|
||||||
case oracle::occi::OCCIREFANY:
|
|
||||||
case oracle::occi::OCCISTREAM:
|
|
||||||
case oracle::occi::OCCICURSOR:
|
|
||||||
case oracle::occi::OCCI_SQLT_FILE:
|
|
||||||
case oracle::occi::OCCI_SQLT_CFILE:
|
|
||||||
case oracle::occi::OCCI_SQLT_REF:
|
|
||||||
case oracle::occi::OCCI_SQLT_CLOB:
|
|
||||||
case oracle::occi::OCCI_SQLT_BLOB:
|
|
||||||
case oracle::occi::OCCI_SQLT_RSET:
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_WARN(occi) << "occi_featureset: Unsupported datatype "
|
|
||||||
<< occi_enums::resolve_datatype(type_oid)
|
|
||||||
<< " (type_oid=" << type_oid << ")";
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default: // shouldn't get here
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_WARN(occi) << "occi_featureset: Unknown datatype "
|
|
||||||
<< "(type_oid=" << type_oid << ")";
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
++feature_id_;
|
|
||||||
|
|
||||||
return feature;
|
|
||||||
}
|
|
||||||
|
|
||||||
return feature_ptr();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void occi_featureset::convert_geometry(SDOGeometry* geom, feature_ptr feature)
|
|
||||||
{
|
|
||||||
int gtype = (int)geom->getSdo_gtype();
|
|
||||||
int dimensions = gtype / 1000;
|
|
||||||
int lrsvalue = (gtype - dimensions * 1000) / 100;
|
|
||||||
int geomtype = (gtype - dimensions * 1000 - lrsvalue * 100);
|
|
||||||
|
|
||||||
const std::vector<Number>& elem_info = geom->getSdo_elem_info();
|
|
||||||
const std::vector<Number>& ordinates = geom->getSdo_ordinates();
|
|
||||||
const int ordinates_size = (int)ordinates.size();
|
|
||||||
|
|
||||||
switch (geomtype)
|
|
||||||
{
|
|
||||||
case SDO_GTYPE_POINT:
|
|
||||||
{
|
|
||||||
SDOPointType* sdopoint = geom->getSdo_point();
|
|
||||||
if (sdopoint && ! sdopoint->isNull())
|
|
||||||
{
|
|
||||||
std::unique_ptr<geometry_type> point = std::make_unique<geometry_type>(mapnik::geometry::geometry_types::Point);
|
|
||||||
point->move_to(sdopoint->getX(), sdopoint->getY());
|
|
||||||
feature->add_geometry(point.release());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SDO_GTYPE_LINE:
|
|
||||||
{
|
|
||||||
if (ordinates_size >= dimensions)
|
|
||||||
{
|
|
||||||
const bool is_single_geom = true;
|
|
||||||
const bool is_point_type = false;
|
|
||||||
convert_ordinates(feature,
|
|
||||||
mapnik::geometry::geometry_types::LineString,
|
|
||||||
elem_info,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_single_geom,
|
|
||||||
is_point_type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SDO_GTYPE_POLYGON:
|
|
||||||
{
|
|
||||||
if (ordinates_size >= dimensions)
|
|
||||||
{
|
|
||||||
const bool is_single_geom = true;
|
|
||||||
const bool is_point_type = false;
|
|
||||||
convert_ordinates(feature,
|
|
||||||
mapnik::geometry::geometry_types::Polygon,
|
|
||||||
elem_info,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_single_geom,
|
|
||||||
is_point_type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SDO_GTYPE_MULTIPOINT:
|
|
||||||
{
|
|
||||||
if (ordinates_size >= dimensions)
|
|
||||||
{
|
|
||||||
const bool is_single_geom = false;
|
|
||||||
const bool is_point_type = true;
|
|
||||||
convert_ordinates(feature,
|
|
||||||
mapnik::geometry::geometry_types::Point,
|
|
||||||
elem_info,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_single_geom,
|
|
||||||
is_point_type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SDO_GTYPE_MULTILINE:
|
|
||||||
{
|
|
||||||
if (ordinates_size >= dimensions)
|
|
||||||
{
|
|
||||||
const bool is_single_geom = false;
|
|
||||||
const bool is_point_type = false;
|
|
||||||
|
|
||||||
convert_ordinates(feature,
|
|
||||||
mapnik::geometry::geometry_types::LineString,
|
|
||||||
elem_info,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_single_geom,
|
|
||||||
is_point_type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SDO_GTYPE_MULTIPOLYGON:
|
|
||||||
{
|
|
||||||
if (ordinates_size >= dimensions)
|
|
||||||
{
|
|
||||||
const bool is_single_geom = false;
|
|
||||||
const bool is_point_type = false;
|
|
||||||
|
|
||||||
convert_ordinates(feature,
|
|
||||||
mapnik::geometry::geometry_types::Polygon,
|
|
||||||
elem_info,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_single_geom,
|
|
||||||
is_point_type);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SDO_GTYPE_COLLECTION:
|
|
||||||
{
|
|
||||||
if (ordinates_size >= dimensions)
|
|
||||||
{
|
|
||||||
const bool is_single_geom = false;
|
|
||||||
const bool is_point_type = false;
|
|
||||||
|
|
||||||
convert_ordinates(feature,
|
|
||||||
mapnik::geometry::geometry_types::Polygon,
|
|
||||||
elem_info,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_single_geom,
|
|
||||||
is_point_type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SDO_GTYPE_UNKNOWN:
|
|
||||||
default:
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_WARN(occi) << "occi_featureset: Unknown oracle enum "
|
|
||||||
<< occi_enums::resolve_gtype(geomtype)
|
|
||||||
<< "(gtype=" << gtype << ")";
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void occi_featureset::convert_ordinates(mapnik::feature_ptr feature,
|
|
||||||
const mapnik::geometry_type::types& geom_type,
|
|
||||||
const std::vector<Number>& elem_info,
|
|
||||||
const std::vector<Number>& ordinates,
|
|
||||||
const int dimensions,
|
|
||||||
const bool is_single_geom,
|
|
||||||
const bool is_point_geom)
|
|
||||||
{
|
|
||||||
const int elem_size = elem_info.size();
|
|
||||||
const int ord_size = ordinates.size();
|
|
||||||
|
|
||||||
if (elem_size >= 0)
|
|
||||||
{
|
|
||||||
int offset = elem_info[0];
|
|
||||||
int etype = elem_info[1];
|
|
||||||
int interp = elem_info[2];
|
|
||||||
|
|
||||||
if (! is_single_geom && elem_size > SDO_ELEM_INFO_SIZE)
|
|
||||||
{
|
|
||||||
geometry_type* geom = new geometry_type(geom_type);
|
|
||||||
|
|
||||||
for (int i = SDO_ELEM_INFO_SIZE; i < elem_size; i+=3)
|
|
||||||
{
|
|
||||||
int next_offset = elem_info[i];
|
|
||||||
int next_etype = elem_info[i + 1];
|
|
||||||
int next_interp = elem_info[i + 2];
|
|
||||||
bool is_linear_element = true;
|
|
||||||
bool is_unknown_etype = false;
|
|
||||||
mapnik::geometry_type::types gtype = mapnik::geometry::geometry_types::Point;
|
|
||||||
|
|
||||||
switch (etype)
|
|
||||||
{
|
|
||||||
case SDO_ETYPE_POINT:
|
|
||||||
if (interp == SDO_INTERPRETATION_POINT) {}
|
|
||||||
if (interp > SDO_INTERPRETATION_POINT) {}
|
|
||||||
gtype = mapnik::geometry::geometry_types::Point;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case SDO_ETYPE_LINESTRING:
|
|
||||||
if (interp == SDO_INTERPRETATION_STRAIGHT) {}
|
|
||||||
if (interp == SDO_INTERPRETATION_CIRCULAR) {}
|
|
||||||
gtype = mapnik::geometry::geometry_types::LineString;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case SDO_ETYPE_POLYGON:
|
|
||||||
case SDO_ETYPE_POLYGON_INTERIOR:
|
|
||||||
if (interp == SDO_INTERPRETATION_STRAIGHT) {}
|
|
||||||
if (interp == SDO_INTERPRETATION_CIRCULAR) {}
|
|
||||||
if (interp == SDO_INTERPRETATION_RECTANGLE) {}
|
|
||||||
if (interp == SDO_INTERPRETATION_CIRCLE) {}
|
|
||||||
gtype = mapnik::geometry::geometry_types::Polygon;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case SDO_ETYPE_COMPOUND_LINESTRING:
|
|
||||||
case SDO_ETYPE_COMPOUND_POLYGON:
|
|
||||||
case SDO_ETYPE_COMPOUND_POLYGON_INTERIOR:
|
|
||||||
// interp = next ETYPE to consider
|
|
||||||
is_linear_element = false;
|
|
||||||
gtype = mapnik::geometry::geometry_types::Polygon;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case SDO_ETYPE_UNKNOWN: // unknown
|
|
||||||
default:
|
|
||||||
is_unknown_etype = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (is_unknown_etype)
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (is_linear_element)
|
|
||||||
{
|
|
||||||
if (geom)
|
|
||||||
{
|
|
||||||
feature->add_geometry(geom);
|
|
||||||
}
|
|
||||||
|
|
||||||
geom = new geometry_type(gtype);
|
|
||||||
fill_geometry_type(geom,
|
|
||||||
offset - 1,
|
|
||||||
next_offset - 1,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_point_geom);
|
|
||||||
}
|
|
||||||
|
|
||||||
offset = next_offset;
|
|
||||||
etype = next_etype;
|
|
||||||
interp = next_interp;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (geom)
|
|
||||||
{
|
|
||||||
feature->add_geometry(geom);
|
|
||||||
geom = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
geometry_type * geom = new geometry_type(geom_type);
|
|
||||||
fill_geometry_type(geom,
|
|
||||||
offset - 1,
|
|
||||||
ord_size,
|
|
||||||
ordinates,
|
|
||||||
dimensions,
|
|
||||||
is_point_geom);
|
|
||||||
|
|
||||||
feature->add_geometry(geom);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void occi_featureset::fill_geometry_type(geometry_type* geom,
|
|
||||||
const int real_offset,
|
|
||||||
const int next_offset,
|
|
||||||
const std::vector<Number>& ordinates,
|
|
||||||
const int dimensions,
|
|
||||||
const bool is_point_geom)
|
|
||||||
{
|
|
||||||
geom->move_to((double) ordinates[real_offset], (double) ordinates[real_offset + 1]);
|
|
||||||
|
|
||||||
if (is_point_geom)
|
|
||||||
{
|
|
||||||
for (int p = real_offset + dimensions; p < next_offset; p += dimensions)
|
|
||||||
{
|
|
||||||
geom->move_to((double) ordinates[p], (double) ordinates[p + 1]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
for (int p = real_offset + dimensions; p < next_offset; p += dimensions)
|
|
||||||
{
|
|
||||||
geom->line_to((double) ordinates[p], (double) ordinates[p + 1]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,77 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OCCI_FEATURESET_HPP
|
|
||||||
#define OCCI_FEATURESET_HPP
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/datasource.hpp>
|
|
||||||
#include <mapnik/unicode.hpp>
|
|
||||||
// stl
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
// oci
|
|
||||||
#include "occi_types.hpp"
|
|
||||||
|
|
||||||
#include <vector>
|
|
||||||
|
|
||||||
class occi_featureset : public mapnik::Featureset
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
occi_featureset(oracle::occi::StatelessConnectionPool* pool,
|
|
||||||
oracle::occi::Connection* conn,
|
|
||||||
mapnik::context_ptr const& ctx,
|
|
||||||
std::string const& sqlstring,
|
|
||||||
std::string const& encoding,
|
|
||||||
bool use_connection_pool,
|
|
||||||
bool use_wkb,
|
|
||||||
unsigned prefetch_rows);
|
|
||||||
virtual ~occi_featureset();
|
|
||||||
mapnik::feature_ptr next();
|
|
||||||
|
|
||||||
private:
|
|
||||||
void convert_geometry (SDOGeometry* geom, mapnik::feature_ptr feature);
|
|
||||||
void convert_ordinates (mapnik::feature_ptr feature,
|
|
||||||
const mapnik::geometry_type::types& geom_type,
|
|
||||||
const std::vector<oracle::occi::Number>& elem_info,
|
|
||||||
const std::vector<oracle::occi::Number>& ordinates,
|
|
||||||
const int dimensions,
|
|
||||||
const bool is_single_geom,
|
|
||||||
const bool is_point_geom);
|
|
||||||
void fill_geometry_type (mapnik::geometry_type* geom,
|
|
||||||
const int real_offset,
|
|
||||||
const int next_offset,
|
|
||||||
const std::vector<oracle::occi::Number>& ordinates,
|
|
||||||
const int dimensions,
|
|
||||||
const bool is_point_geom);
|
|
||||||
|
|
||||||
occi_connection_ptr conn_;
|
|
||||||
oracle::occi::ResultSet* rs_;
|
|
||||||
const std::unique_ptr<mapnik::transcoder> tr_;
|
|
||||||
mapnik::value_integer feature_id_;
|
|
||||||
mapnik::context_ptr ctx_;
|
|
||||||
bool use_wkb_;
|
|
||||||
std::vector<char> buffer_;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OCCI_FEATURESET_HPP
|
|
|
@ -1,91 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software, you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation, either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY, without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library, if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#include "occi_types.hpp"
|
|
||||||
|
|
||||||
std::string occi_enums::resolve_gtype(int gtype)
|
|
||||||
{
|
|
||||||
switch (gtype)
|
|
||||||
{
|
|
||||||
case SDO_GTYPE_UNKNOWN: return "SDO_GTYPE_UNKNOWN";
|
|
||||||
case SDO_GTYPE_POINT: return "SDO_GTYPE_POINT";
|
|
||||||
case SDO_GTYPE_LINE: return "SDO_GTYPE_LINE";
|
|
||||||
case SDO_GTYPE_POLYGON: return "SDO_GTYPE_POLYGON";
|
|
||||||
case SDO_GTYPE_MULTIPOINT: return "SDO_GTYPE_MULTIPOINT";
|
|
||||||
case SDO_GTYPE_MULTILINE: return "SDO_GTYPE_MULTILINE";
|
|
||||||
case SDO_GTYPE_MULTIPOLYGON: return "SDO_GTYPE_MULTIPOLYGON";
|
|
||||||
case SDO_GTYPE_COLLECTION: return "SDO_GTYPE_COLLECTION";
|
|
||||||
default: return "<unknown SDO_GTYPE>";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string occi_enums::resolve_etype(int etype)
|
|
||||||
{
|
|
||||||
switch (etype)
|
|
||||||
{
|
|
||||||
case SDO_ETYPE_UNKNOWN: return "SDO_ETYPE_UNKNOWN";
|
|
||||||
case SDO_ETYPE_POINT: return "SDO_ETYPE_POINT";
|
|
||||||
case SDO_ETYPE_LINESTRING: return "SDO_ETYPE_LINESTRING";
|
|
||||||
case SDO_ETYPE_POLYGON: return "SDO_ETYPE_POLYGON";
|
|
||||||
case SDO_ETYPE_POLYGON_INTERIOR: return "SDO_ETYPE_POLYGON_INTERIOR";
|
|
||||||
case SDO_ETYPE_COMPOUND_LINESTRING: return "SDO_ETYPE_COMPOUND_LINESTRING";
|
|
||||||
case SDO_ETYPE_COMPOUND_POLYGON: return "SDO_ETYPE_COMPOUND_POLYGON";
|
|
||||||
case SDO_ETYPE_COMPOUND_POLYGON_INTERIOR: return "SDO_ETYPE_COMPOUND_POLYGON_INTERIOR";
|
|
||||||
default: return "<unknown SDO_ETYPE>";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string occi_enums::resolve_datatype(int type_id)
|
|
||||||
{
|
|
||||||
switch (type_id)
|
|
||||||
{
|
|
||||||
case oracle::occi::OCCIINT: return "OCCIINT";
|
|
||||||
case oracle::occi::OCCIUNSIGNED_INT: return "OCCIUNSIGNED_INT";
|
|
||||||
case oracle::occi::OCCIFLOAT: return "OCCIFLOAT";
|
|
||||||
case oracle::occi::OCCIBFLOAT: return "OCCIBFLOAT";
|
|
||||||
case oracle::occi::OCCIDOUBLE: return "OCCIDOUBLE";
|
|
||||||
case oracle::occi::OCCIBDOUBLE: return "OCCIBDOUBLE";
|
|
||||||
case oracle::occi::OCCINUMBER: return "OCCINUMBER";
|
|
||||||
case oracle::occi::OCCI_SQLT_NUM: return "OCCI_SQLT_NUM";
|
|
||||||
case oracle::occi::OCCICHAR: return "OCCICHAR";
|
|
||||||
case oracle::occi::OCCISTRING: return "OCCISTRING";
|
|
||||||
case oracle::occi::OCCI_SQLT_AFC: return "OCCI_SQLT_AFC";
|
|
||||||
case oracle::occi::OCCI_SQLT_AVC: return "OCCI_SQLT_AVC";
|
|
||||||
case oracle::occi::OCCI_SQLT_CHR: return "OCCI_SQLT_CHR";
|
|
||||||
case oracle::occi::OCCI_SQLT_LVC: return "OCCI_SQLT_LVC";
|
|
||||||
case oracle::occi::OCCI_SQLT_LNG: return "OCCI_SQLT_LNG";
|
|
||||||
case oracle::occi::OCCI_SQLT_STR: return "OCCI_SQLT_STR";
|
|
||||||
case oracle::occi::OCCI_SQLT_VCS: return "OCCI_SQLT_VCS";
|
|
||||||
case oracle::occi::OCCI_SQLT_VNU: return "OCCI_SQLT_VNU";
|
|
||||||
case oracle::occi::OCCI_SQLT_VBI: return "OCCI_SQLT_VBI";
|
|
||||||
case oracle::occi::OCCI_SQLT_VST: return "OCCI_SQLT_VST";
|
|
||||||
case oracle::occi::OCCI_SQLT_RDD: return "OCCI_SQLT_RDD";
|
|
||||||
case oracle::occi::OCCIDATE: return "OCCIDATE";
|
|
||||||
case oracle::occi::OCCITIMESTAMP: return "OCCITIMESTAMP";
|
|
||||||
case oracle::occi::OCCI_SQLT_DAT: return "OCCI_SQLT_DAT";
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP: return "OCCI_SQLT_TIMESTAMP";
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP_LTZ: return "OCCI_SQLT_TIMESTAMP_LTZ";
|
|
||||||
case oracle::occi::OCCI_SQLT_TIMESTAMP_TZ: return "OCCI_SQLT_TIMESTAMP_TZ";
|
|
||||||
case oracle::occi::OCCIPOBJECT: return "OCCIPOBJECT";
|
|
||||||
default: return "<unknown ATTR_DATA_TYPE>";
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,265 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software, you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation, either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY, without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library, if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OCCI_TYPES_HPP
|
|
||||||
#define OCCI_TYPES_HPP
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/util/singleton.hpp>
|
|
||||||
|
|
||||||
// occi
|
|
||||||
#include <occi.h>
|
|
||||||
|
|
||||||
// ott generated SDOGeometry classes
|
|
||||||
#include "spatial_classesh.h"
|
|
||||||
#include "spatial_classesm.h"
|
|
||||||
|
|
||||||
// check for oracle support
|
|
||||||
#if OCCI_MAJOR_VERSION >= 10 && OCCI_MINOR_VERSION >= 1
|
|
||||||
// We have at least ORACLE 10g >= 10.2.0.X
|
|
||||||
#else
|
|
||||||
#error Only ORACLE 10g >= 10.2.0.X is supported !
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// geometry types definitions
|
|
||||||
enum
|
|
||||||
{
|
|
||||||
SDO_GTYPE_UNKNOWN = 0,
|
|
||||||
SDO_GTYPE_POINT = 1,
|
|
||||||
SDO_GTYPE_LINE = 2,
|
|
||||||
SDO_GTYPE_POLYGON = 3,
|
|
||||||
SDO_GTYPE_COLLECTION = 4,
|
|
||||||
SDO_GTYPE_MULTIPOINT = 5,
|
|
||||||
SDO_GTYPE_MULTILINE = 6,
|
|
||||||
SDO_GTYPE_MULTIPOLYGON = 7,
|
|
||||||
|
|
||||||
SDO_GTYPE_2DPOINT = 2001,
|
|
||||||
SDO_GTYPE_2DLINE = 2002,
|
|
||||||
SDO_GTYPE_2DPOLYGON = 2003,
|
|
||||||
SDO_GTYPE_2DMULTIPOINT = 2005,
|
|
||||||
SDO_GTYPE_2DMULTILINE = 2006,
|
|
||||||
SDO_GTYPE_2DMULTIPOLYGON = 2007,
|
|
||||||
|
|
||||||
SDO_ELEM_INFO_SIZE = 3,
|
|
||||||
|
|
||||||
SDO_ETYPE_UNKNOWN = 0,
|
|
||||||
SDO_ETYPE_POINT = 1,
|
|
||||||
SDO_ETYPE_LINESTRING = 2,
|
|
||||||
SDO_ETYPE_POLYGON = 1003,
|
|
||||||
SDO_ETYPE_POLYGON_INTERIOR = 2003,
|
|
||||||
SDO_ETYPE_COMPOUND_LINESTRING = 4,
|
|
||||||
SDO_ETYPE_COMPOUND_POLYGON = 1005,
|
|
||||||
SDO_ETYPE_COMPOUND_POLYGON_INTERIOR = 2005,
|
|
||||||
|
|
||||||
SDO_INTERPRETATION_POINT = 1,
|
|
||||||
SDO_INTERPRETATION_RECTANGLE = 3,
|
|
||||||
SDO_INTERPRETATION_CIRCLE = 4,
|
|
||||||
SDO_INTERPRETATION_STRAIGHT = 1,
|
|
||||||
SDO_INTERPRETATION_CIRCULAR = 2
|
|
||||||
};
|
|
||||||
|
|
||||||
class occi_environment : public mapnik::singleton<occi_environment, mapnik::CreateStatic>
|
|
||||||
{
|
|
||||||
friend class mapnik::CreateStatic<occi_environment>;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
oracle::occi::Environment* get_environment()
|
|
||||||
{
|
|
||||||
return env_;
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::Connection* create_connection(
|
|
||||||
const std::string& user,
|
|
||||||
const std::string& password,
|
|
||||||
const std::string& host)
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_environment: create_connection";
|
|
||||||
|
|
||||||
return env_->createConnection(user, password, host);
|
|
||||||
}
|
|
||||||
|
|
||||||
void destroy_connection(oracle::occi::Connection* conn)
|
|
||||||
{
|
|
||||||
env_->terminateConnection(conn);
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::StatelessConnectionPool* create_pool(
|
|
||||||
const std::string& user,
|
|
||||||
const std::string& password,
|
|
||||||
const std::string& host,
|
|
||||||
int max_size,
|
|
||||||
int initial_size,
|
|
||||||
int incr_size)
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_environment: create_pool";
|
|
||||||
|
|
||||||
return env_->createStatelessConnectionPool(
|
|
||||||
user,
|
|
||||||
password,
|
|
||||||
host,
|
|
||||||
max_size,
|
|
||||||
initial_size,
|
|
||||||
incr_size,
|
|
||||||
oracle::occi::StatelessConnectionPool::HOMOGENEOUS);
|
|
||||||
}
|
|
||||||
|
|
||||||
void destroy_pool(oracle::occi::StatelessConnectionPool* pool)
|
|
||||||
{
|
|
||||||
env_->terminateStatelessConnectionPool(
|
|
||||||
pool,
|
|
||||||
oracle::occi::StatelessConnectionPool::SPD_FORCE);
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
occi_environment()
|
|
||||||
: env_(0)
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_environment: constructor";
|
|
||||||
|
|
||||||
env_ = oracle::occi::Environment::createEnvironment(
|
|
||||||
(oracle::occi::Environment::Mode)(oracle::occi::Environment::OBJECT
|
|
||||||
| oracle::occi::Environment::THREADED_MUTEXED));
|
|
||||||
RegisterClasses(env_);
|
|
||||||
}
|
|
||||||
|
|
||||||
~occi_environment()
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_environment: destructor";
|
|
||||||
|
|
||||||
oracle::occi::Environment::terminateEnvironment(env_);
|
|
||||||
env_ = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::Environment* env_;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
class occi_connection_ptr
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
explicit occi_connection_ptr()
|
|
||||||
: pool_(0),
|
|
||||||
conn_(0),
|
|
||||||
stmt_(0),
|
|
||||||
rs_(0),
|
|
||||||
owns_connection_(false)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
~occi_connection_ptr()
|
|
||||||
{
|
|
||||||
close_query(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
void set_pool(oracle::occi::StatelessConnectionPool* pool)
|
|
||||||
{
|
|
||||||
close_query(true);
|
|
||||||
|
|
||||||
pool_ = pool;
|
|
||||||
conn_ = pool_->getConnection();
|
|
||||||
owns_connection_ = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void set_connection(oracle::occi::Connection* conn, bool owns_connection)
|
|
||||||
{
|
|
||||||
close_query(true);
|
|
||||||
|
|
||||||
pool_ = 0;
|
|
||||||
conn_ = conn;
|
|
||||||
owns_connection_ = owns_connection;
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::ResultSet* execute_query(std::string const& s, const unsigned prefetch = 0)
|
|
||||||
{
|
|
||||||
close_query(false);
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(occi) << "occi_connection_ptr: " << s;
|
|
||||||
|
|
||||||
stmt_ = conn_->createStatement(s);
|
|
||||||
|
|
||||||
if (prefetch > 0)
|
|
||||||
{
|
|
||||||
stmt_->setPrefetchMemorySize(0);
|
|
||||||
stmt_->setPrefetchRowCount(prefetch);
|
|
||||||
}
|
|
||||||
|
|
||||||
rs_ = stmt_->executeQuery();
|
|
||||||
|
|
||||||
return rs_;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
void close_query(const bool release_connection)
|
|
||||||
{
|
|
||||||
if (conn_)
|
|
||||||
{
|
|
||||||
if (stmt_)
|
|
||||||
{
|
|
||||||
if (rs_)
|
|
||||||
{
|
|
||||||
stmt_->closeResultSet(rs_);
|
|
||||||
rs_ = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
conn_->terminateStatement(stmt_);
|
|
||||||
stmt_ = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (release_connection)
|
|
||||||
{
|
|
||||||
if (pool_)
|
|
||||||
{
|
|
||||||
pool_->releaseConnection(conn_);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (owns_connection_)
|
|
||||||
{
|
|
||||||
occi_environment::instance().destroy_connection(conn_);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
conn_ = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::StatelessConnectionPool* pool_;
|
|
||||||
oracle::occi::Connection* conn_;
|
|
||||||
oracle::occi::Statement* stmt_;
|
|
||||||
oracle::occi::ResultSet* rs_;
|
|
||||||
bool owns_connection_;
|
|
||||||
};
|
|
||||||
|
|
||||||
class occi_enums
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
|
|
||||||
static std::string resolve_gtype(int gtype);
|
|
||||||
static std::string resolve_etype(int etype);
|
|
||||||
static std::string resolve_datatype(int type_id);
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OCCI_TYPES_HPP
|
|
|
@ -1,147 +0,0 @@
|
||||||
#ifndef SPATIAL_CLASSESH_ORACLE
|
|
||||||
# define SPATIAL_CLASSESH_ORACLE
|
|
||||||
|
|
||||||
#ifndef OCCI_ORACLE
|
|
||||||
# include <occi.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
class SDOPointType;
|
|
||||||
class SDOGeometry;
|
|
||||||
|
|
||||||
/************************************************************/
|
|
||||||
// generated declarations for the SDO_POINT_TYPE object type.
|
|
||||||
/************************************************************/
|
|
||||||
|
|
||||||
class SDOPointType : public oracle::occi::PObject {
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
oracle::occi::Number X;
|
|
||||||
oracle::occi::Number Y;
|
|
||||||
oracle::occi::Number Z;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
oracle::occi::Number getX() const;
|
|
||||||
|
|
||||||
void setX(const oracle::occi::Number &value);
|
|
||||||
|
|
||||||
oracle::occi::Number getY() const;
|
|
||||||
|
|
||||||
void setY(const oracle::occi::Number &value);
|
|
||||||
|
|
||||||
oracle::occi::Number getZ() const;
|
|
||||||
|
|
||||||
void setZ(const oracle::occi::Number &value);
|
|
||||||
|
|
||||||
void *operator new(size_t size);
|
|
||||||
|
|
||||||
void *operator new(size_t size, const oracle::occi::Connection * sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string& table);
|
|
||||||
|
|
||||||
void *operator new(size_t, void *ctxOCCI_);
|
|
||||||
|
|
||||||
void *operator new(size_t size, const oracle::occi::Connection *sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableSchema,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeSchema);
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::string getSQLTypeName() const;
|
|
||||||
|
|
||||||
void getSQLTypeName(oracle::occi::Environment *env, void **schemaName,
|
|
||||||
unsigned int &schemaNameLen, void **typeName,
|
|
||||||
unsigned int &typeNameLen) const;
|
|
||||||
|
|
||||||
SDOPointType();
|
|
||||||
|
|
||||||
SDOPointType(void *ctxOCCI_) : oracle::occi::PObject (ctxOCCI_) { }
|
|
||||||
|
|
||||||
static void *readSQL(void *ctxOCCI_);
|
|
||||||
|
|
||||||
virtual void readSQL(oracle::occi::AnyData& streamOCCI_);
|
|
||||||
|
|
||||||
static void writeSQL(void *objOCCI_, void *ctxOCCI_);
|
|
||||||
|
|
||||||
virtual void writeSQL(oracle::occi::AnyData& streamOCCI_);
|
|
||||||
|
|
||||||
~SDOPointType();
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
/************************************************************/
|
|
||||||
// generated declarations for the SDO_GEOMETRY object type.
|
|
||||||
/************************************************************/
|
|
||||||
|
|
||||||
class SDOGeometry : public oracle::occi::PObject {
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
oracle::occi::Number SDO_GTYPE;
|
|
||||||
oracle::occi::Number SDO_SRID;
|
|
||||||
SDOPointType * SDO_POINT;
|
|
||||||
OCCI_STD_NAMESPACE::vector< oracle::occi::Number > SDO_ELEM_INFO;
|
|
||||||
OCCI_STD_NAMESPACE::vector< oracle::occi::Number > SDO_ORDINATES;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
oracle::occi::Number getSdo_gtype() const;
|
|
||||||
|
|
||||||
void setSdo_gtype(const oracle::occi::Number &value);
|
|
||||||
|
|
||||||
oracle::occi::Number getSdo_srid() const;
|
|
||||||
|
|
||||||
void setSdo_srid(const oracle::occi::Number &value);
|
|
||||||
|
|
||||||
SDOPointType * getSdo_point() const;
|
|
||||||
|
|
||||||
void setSdo_point(SDOPointType * value);
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& getSdo_elem_info();
|
|
||||||
|
|
||||||
const OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& getSdo_elem_info() const;
|
|
||||||
|
|
||||||
void setSdo_elem_info(const OCCI_STD_NAMESPACE::vector< oracle::occi::Number > &value);
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& getSdo_ordinates();
|
|
||||||
|
|
||||||
const OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& getSdo_ordinates() const;
|
|
||||||
|
|
||||||
void setSdo_ordinates(const OCCI_STD_NAMESPACE::vector< oracle::occi::Number > &value);
|
|
||||||
|
|
||||||
void *operator new(size_t size);
|
|
||||||
|
|
||||||
void *operator new(size_t size, const oracle::occi::Connection * sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string& table);
|
|
||||||
|
|
||||||
void *operator new(size_t, void *ctxOCCI_);
|
|
||||||
|
|
||||||
void *operator new(size_t size, const oracle::occi::Connection *sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableSchema,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeSchema);
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::string getSQLTypeName() const;
|
|
||||||
|
|
||||||
void getSQLTypeName(oracle::occi::Environment *env, void **schemaName,
|
|
||||||
unsigned int &schemaNameLen, void **typeName,
|
|
||||||
unsigned int &typeNameLen) const;
|
|
||||||
|
|
||||||
SDOGeometry();
|
|
||||||
|
|
||||||
SDOGeometry(void *ctxOCCI_) : oracle::occi::PObject (ctxOCCI_) { }
|
|
||||||
|
|
||||||
static void *readSQL(void *ctxOCCI_);
|
|
||||||
|
|
||||||
virtual void readSQL(oracle::occi::AnyData& streamOCCI_);
|
|
||||||
|
|
||||||
static void writeSQL(void *objOCCI_, void *ctxOCCI_);
|
|
||||||
|
|
||||||
virtual void writeSQL(oracle::occi::AnyData& streamOCCI_);
|
|
||||||
|
|
||||||
~SDOGeometry();
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif
|
|
|
@ -1,11 +0,0 @@
|
||||||
|
|
||||||
#ifndef SPATIAL_CLASSESM_ORACLE
|
|
||||||
# include "spatial_classesm.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
void RegisterClasses(oracle::occi::Environment* envOCCI_)
|
|
||||||
{
|
|
||||||
oracle::occi::Map *mapOCCI_ = envOCCI_->getMap();
|
|
||||||
mapOCCI_->put("MDSYS.SDO_POINT_TYPE", &SDOPointType::readSQL, &SDOPointType::writeSQL);
|
|
||||||
mapOCCI_->put("MDSYS.SDO_GEOMETRY", &SDOGeometry::readSQL, &SDOGeometry::writeSQL);
|
|
||||||
}
|
|
|
@ -1,14 +0,0 @@
|
||||||
#ifndef SPATIAL_CLASSESM_ORACLE
|
|
||||||
# define SPATIAL_CLASSESM_ORACLE
|
|
||||||
|
|
||||||
#ifndef OCCI_ORACLE
|
|
||||||
# include <occi.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef SPATIAL_CLASSESH_ORACLE
|
|
||||||
# include "spatial_classesh.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
void RegisterClasses(oracle::occi::Environment* envOCCI_);
|
|
||||||
|
|
||||||
#endif
|
|
|
@ -1,312 +0,0 @@
|
||||||
#ifndef SPATIAL_CLASSESH_ORACLE
|
|
||||||
# include "spatial_classesh.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
/*****************************************************************/
|
|
||||||
// generated method implementations for the SDO_POINT_TYPE object type.
|
|
||||||
/*****************************************************************/
|
|
||||||
|
|
||||||
oracle::occi::Number SDOPointType::getX() const
|
|
||||||
{
|
|
||||||
return X;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOPointType::setX(const oracle::occi::Number &value)
|
|
||||||
{
|
|
||||||
X = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::Number SDOPointType::getY() const
|
|
||||||
{
|
|
||||||
return Y;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOPointType::setY(const oracle::occi::Number &value)
|
|
||||||
{
|
|
||||||
Y = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::Number SDOPointType::getZ() const
|
|
||||||
{
|
|
||||||
return Z;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOPointType::setZ(const oracle::occi::Number &value)
|
|
||||||
{
|
|
||||||
Z = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOPointType::operator new(size_t size)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size);
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOPointType::operator new(size_t size, const oracle::occi::Connection * sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string& table)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size, sess, table,
|
|
||||||
(char *) "MDSYS.SDO_POINT_TYPE");
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOPointType::operator new(size_t size, void *ctxOCCI_)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size, ctxOCCI_);
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOPointType::operator new(size_t size,
|
|
||||||
const oracle::occi::Connection *sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableSchema,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeSchema)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size, sess, tableName,
|
|
||||||
typeName, tableSchema, typeSchema);
|
|
||||||
}
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::string SDOPointType::getSQLTypeName() const
|
|
||||||
{
|
|
||||||
return OCCI_STD_NAMESPACE::string("MDSYS.SDO_POINT_TYPE");
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOPointType::getSQLTypeName(oracle::occi::Environment *env, void **schemaName,
|
|
||||||
unsigned int &schemaNameLen, void **typeName, unsigned int &typeNameLen) const
|
|
||||||
{
|
|
||||||
PObject::getSQLTypeName(env, &SDOPointType::readSQL, schemaName,
|
|
||||||
schemaNameLen, typeName, typeNameLen);
|
|
||||||
}
|
|
||||||
|
|
||||||
SDOPointType::SDOPointType()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOPointType::readSQL(void *ctxOCCI_)
|
|
||||||
{
|
|
||||||
SDOPointType *objOCCI_ = new(ctxOCCI_) SDOPointType(ctxOCCI_);
|
|
||||||
oracle::occi::AnyData streamOCCI_(ctxOCCI_);
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (streamOCCI_.isNull())
|
|
||||||
objOCCI_->setNull();
|
|
||||||
else
|
|
||||||
objOCCI_->readSQL(streamOCCI_);
|
|
||||||
}
|
|
||||||
catch (oracle::occi::SQLException& excep)
|
|
||||||
{
|
|
||||||
delete objOCCI_;
|
|
||||||
excep.setErrorCtx(ctxOCCI_);
|
|
||||||
return (void *)nullptr;
|
|
||||||
}
|
|
||||||
return (void *)objOCCI_;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOPointType::readSQL(oracle::occi::AnyData& streamOCCI_)
|
|
||||||
{
|
|
||||||
X = streamOCCI_.getNumber();
|
|
||||||
Y = streamOCCI_.getNumber();
|
|
||||||
Z = streamOCCI_.getNumber();
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOPointType::writeSQL(void *objectOCCI_, void *ctxOCCI_)
|
|
||||||
{
|
|
||||||
SDOPointType *objOCCI_ = (SDOPointType *) objectOCCI_;
|
|
||||||
oracle::occi::AnyData streamOCCI_(ctxOCCI_);
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (objOCCI_->isNull())
|
|
||||||
streamOCCI_.setNull();
|
|
||||||
else
|
|
||||||
objOCCI_->writeSQL(streamOCCI_);
|
|
||||||
}
|
|
||||||
catch (oracle::occi::SQLException& excep)
|
|
||||||
{
|
|
||||||
excep.setErrorCtx(ctxOCCI_);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOPointType::writeSQL(oracle::occi::AnyData& streamOCCI_)
|
|
||||||
{
|
|
||||||
streamOCCI_.setNumber(X);
|
|
||||||
streamOCCI_.setNumber(Y);
|
|
||||||
streamOCCI_.setNumber(Z);
|
|
||||||
}
|
|
||||||
|
|
||||||
SDOPointType::~SDOPointType()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/*****************************************************************/
|
|
||||||
// generated method implementations for the SDO_GEOMETRY object type.
|
|
||||||
/*****************************************************************/
|
|
||||||
|
|
||||||
oracle::occi::Number SDOGeometry::getSdo_gtype() const
|
|
||||||
{
|
|
||||||
return SDO_GTYPE;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::setSdo_gtype(const oracle::occi::Number &value)
|
|
||||||
{
|
|
||||||
SDO_GTYPE = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
oracle::occi::Number SDOGeometry::getSdo_srid() const
|
|
||||||
{
|
|
||||||
return SDO_SRID;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::setSdo_srid(const oracle::occi::Number &value)
|
|
||||||
{
|
|
||||||
SDO_SRID = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
SDOPointType * SDOGeometry::getSdo_point() const
|
|
||||||
{
|
|
||||||
return SDO_POINT;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::setSdo_point(SDOPointType * value)
|
|
||||||
{
|
|
||||||
SDO_POINT = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& SDOGeometry::getSdo_elem_info()
|
|
||||||
{
|
|
||||||
return SDO_ELEM_INFO;
|
|
||||||
}
|
|
||||||
|
|
||||||
const OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& SDOGeometry::getSdo_elem_info() const
|
|
||||||
{
|
|
||||||
return SDO_ELEM_INFO;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::setSdo_elem_info(const OCCI_STD_NAMESPACE::vector< oracle::occi::Number > &value)
|
|
||||||
{
|
|
||||||
SDO_ELEM_INFO = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& SDOGeometry::getSdo_ordinates()
|
|
||||||
{
|
|
||||||
return SDO_ORDINATES;
|
|
||||||
}
|
|
||||||
|
|
||||||
const OCCI_STD_NAMESPACE::vector< oracle::occi::Number >& SDOGeometry::getSdo_ordinates() const
|
|
||||||
{
|
|
||||||
return SDO_ORDINATES;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::setSdo_ordinates(const OCCI_STD_NAMESPACE::vector< oracle::occi::Number > &value)
|
|
||||||
{
|
|
||||||
SDO_ORDINATES = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOGeometry::operator new(size_t size)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size);
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOGeometry::operator new(size_t size, const oracle::occi::Connection * sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string& table)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size, sess, table,
|
|
||||||
(char *) "MDSYS.SDO_GEOMETRY");
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOGeometry::operator new(size_t size, void *ctxOCCI_)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size, ctxOCCI_);
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOGeometry::operator new(size_t size,
|
|
||||||
const oracle::occi::Connection *sess,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeName,
|
|
||||||
const OCCI_STD_NAMESPACE::string &tableSchema,
|
|
||||||
const OCCI_STD_NAMESPACE::string &typeSchema)
|
|
||||||
{
|
|
||||||
return oracle::occi::PObject::operator new(size, sess, tableName,
|
|
||||||
typeName, tableSchema, typeSchema);
|
|
||||||
}
|
|
||||||
|
|
||||||
OCCI_STD_NAMESPACE::string SDOGeometry::getSQLTypeName() const
|
|
||||||
{
|
|
||||||
return OCCI_STD_NAMESPACE::string("MDSYS.SDO_GEOMETRY");
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::getSQLTypeName(oracle::occi::Environment *env, void **schemaName,
|
|
||||||
unsigned int &schemaNameLen, void **typeName, unsigned int &typeNameLen) const
|
|
||||||
{
|
|
||||||
PObject::getSQLTypeName(env, &SDOGeometry::readSQL, schemaName,
|
|
||||||
schemaNameLen, typeName, typeNameLen);
|
|
||||||
}
|
|
||||||
|
|
||||||
SDOGeometry::SDOGeometry()
|
|
||||||
{
|
|
||||||
SDO_POINT = (SDOPointType *) 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void *SDOGeometry::readSQL(void *ctxOCCI_)
|
|
||||||
{
|
|
||||||
SDOGeometry *objOCCI_ = new(ctxOCCI_) SDOGeometry(ctxOCCI_);
|
|
||||||
oracle::occi::AnyData streamOCCI_(ctxOCCI_);
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (streamOCCI_.isNull())
|
|
||||||
objOCCI_->setNull();
|
|
||||||
else
|
|
||||||
objOCCI_->readSQL(streamOCCI_);
|
|
||||||
}
|
|
||||||
catch (oracle::occi::SQLException& excep)
|
|
||||||
{
|
|
||||||
delete objOCCI_;
|
|
||||||
excep.setErrorCtx(ctxOCCI_);
|
|
||||||
return (void *)nullptr;
|
|
||||||
}
|
|
||||||
return (void *)objOCCI_;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::readSQL(oracle::occi::AnyData& streamOCCI_)
|
|
||||||
{
|
|
||||||
SDO_GTYPE = streamOCCI_.getNumber();
|
|
||||||
SDO_SRID = streamOCCI_.getNumber();
|
|
||||||
SDO_POINT = (SDOPointType *) streamOCCI_.getObject(&SDOPointType::readSQL);
|
|
||||||
oracle::occi::getVector(streamOCCI_, SDO_ELEM_INFO);
|
|
||||||
oracle::occi::getVector(streamOCCI_, SDO_ORDINATES);
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::writeSQL(void *objectOCCI_, void *ctxOCCI_)
|
|
||||||
{
|
|
||||||
SDOGeometry *objOCCI_ = (SDOGeometry *) objectOCCI_;
|
|
||||||
oracle::occi::AnyData streamOCCI_(ctxOCCI_);
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (objOCCI_->isNull())
|
|
||||||
streamOCCI_.setNull();
|
|
||||||
else
|
|
||||||
objOCCI_->writeSQL(streamOCCI_);
|
|
||||||
}
|
|
||||||
catch (oracle::occi::SQLException& excep)
|
|
||||||
{
|
|
||||||
excep.setErrorCtx(ctxOCCI_);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
void SDOGeometry::writeSQL(oracle::occi::AnyData& streamOCCI_)
|
|
||||||
{
|
|
||||||
streamOCCI_.setNumber(SDO_GTYPE);
|
|
||||||
streamOCCI_.setNumber(SDO_SRID);
|
|
||||||
streamOCCI_.setObject(SDO_POINT);
|
|
||||||
oracle::occi::setVector(streamOCCI_, SDO_ELEM_INFO);
|
|
||||||
oracle::occi::setVector(streamOCCI_, SDO_ORDINATES);
|
|
||||||
}
|
|
||||||
|
|
||||||
SDOGeometry::~SDOGeometry()
|
|
||||||
{
|
|
||||||
delete SDO_POINT;
|
|
||||||
}
|
|
|
@ -1,4 +0,0 @@
|
||||||
TYPE MDSYS.SDO_POINT_TYPE AS SDOPointType
|
|
||||||
TYPE MDSYS.SDO_GEOMETRY AS SDOGeometry
|
|
||||||
|
|
||||||
|
|
|
@ -1,75 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#include "basiccurl.h"
|
|
||||||
|
|
||||||
#include <iostream>
|
|
||||||
#include <cstring>
|
|
||||||
|
|
||||||
CURL_LOAD_DATA* grab_http_response(const char* url)
|
|
||||||
{
|
|
||||||
CURL_LOAD_DATA* data;
|
|
||||||
|
|
||||||
CURL* curl = curl_easy_init();
|
|
||||||
|
|
||||||
if(curl)
|
|
||||||
{
|
|
||||||
data = do_grab(curl, url);
|
|
||||||
curl_easy_cleanup(curl);
|
|
||||||
return data;
|
|
||||||
}
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
CURL_LOAD_DATA* do_grab(CURL* curl,const char* url)
|
|
||||||
{
|
|
||||||
CURL_LOAD_DATA* data = (CURL_LOAD_DATA*)malloc(sizeof(CURL_LOAD_DATA));
|
|
||||||
data->data = nullptr;
|
|
||||||
data->nbytes = 0;
|
|
||||||
|
|
||||||
curl_easy_setopt(curl, CURLOPT_URL, url);
|
|
||||||
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, response_callback);
|
|
||||||
curl_easy_setopt(curl, CURLOPT_WRITEDATA, data);
|
|
||||||
|
|
||||||
CURLcode res = curl_easy_perform(curl);
|
|
||||||
if (res !=0) {
|
|
||||||
std::clog << "error grabbing data\n";
|
|
||||||
}
|
|
||||||
|
|
||||||
return data;
|
|
||||||
}
|
|
||||||
|
|
||||||
size_t response_callback(void* ptr, size_t size, size_t nmemb, void* d)
|
|
||||||
{
|
|
||||||
size_t rsize = size * nmemb;
|
|
||||||
CURL_LOAD_DATA* data = (CURL_LOAD_DATA*)d;
|
|
||||||
|
|
||||||
// fprintf(stderr,"rsize is %d\n", rsize);
|
|
||||||
|
|
||||||
data->data = (char*)realloc(data->data, (data->nbytes + rsize) * sizeof(char));
|
|
||||||
std::memcpy(&(data->data[data->nbytes]), ptr, rsize);
|
|
||||||
data->nbytes += rsize;
|
|
||||||
|
|
||||||
// fprintf(stderr,"data->nbytes is %d\n", data->nbytes);
|
|
||||||
|
|
||||||
return rsize;
|
|
||||||
}
|
|
|
@ -1,40 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2011 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef BASICCURL_H
|
|
||||||
#define BASICCURL_H
|
|
||||||
|
|
||||||
#include <curl/curl.h>
|
|
||||||
#include <cstdlib>
|
|
||||||
#include <cstring>
|
|
||||||
|
|
||||||
typedef struct
|
|
||||||
{
|
|
||||||
char *data;
|
|
||||||
int nbytes;
|
|
||||||
} CURL_LOAD_DATA;
|
|
||||||
|
|
||||||
CURL_LOAD_DATA *grab_http_response(const char *url);
|
|
||||||
CURL_LOAD_DATA *do_grab(CURL *curl, const char *url);
|
|
||||||
size_t response_callback(void *ptr ,size_t size, size_t nmemb, void *data);
|
|
||||||
|
|
||||||
#endif // BASICCURL_H
|
|
|
@ -1,69 +0,0 @@
|
||||||
#
|
|
||||||
# This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
#
|
|
||||||
# Copyright (C) 2015 Artem Pavlenko
|
|
||||||
#
|
|
||||||
# Mapnik is free software; you can redistribute it and/or
|
|
||||||
# modify it under the terms of the GNU Lesser General Public
|
|
||||||
# License as published by the Free Software Foundation; either
|
|
||||||
# version 2.1 of the License, or (at your option) any later version.
|
|
||||||
#
|
|
||||||
# This library is distributed in the hope that it will be useful,
|
|
||||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
# Lesser General Public License for more details.
|
|
||||||
#
|
|
||||||
# You should have received a copy of the GNU Lesser General Public
|
|
||||||
# License along with this library; if not, write to the Free Software
|
|
||||||
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
#
|
|
||||||
#
|
|
||||||
|
|
||||||
Import ('plugin_base')
|
|
||||||
Import ('env')
|
|
||||||
from copy import copy
|
|
||||||
|
|
||||||
PLUGIN_NAME = 'osm'
|
|
||||||
|
|
||||||
plugin_env = plugin_base.Clone()
|
|
||||||
|
|
||||||
plugin_sources = Split(
|
|
||||||
"""
|
|
||||||
%(PLUGIN_NAME)s.cpp
|
|
||||||
%(PLUGIN_NAME)s_datasource.cpp
|
|
||||||
%(PLUGIN_NAME)s_featureset.cpp
|
|
||||||
osmparser.cpp
|
|
||||||
dataset_deliverer.cpp
|
|
||||||
""" % locals()
|
|
||||||
)
|
|
||||||
|
|
||||||
plugin_env['LIBS'] = []
|
|
||||||
plugin_env.Append(LIBS='xml2')
|
|
||||||
|
|
||||||
# Link Library to Dependencies
|
|
||||||
libraries = copy(plugin_env['LIBS'])
|
|
||||||
libraries.append(env['ICU_LIB_NAME'])
|
|
||||||
libraries.append('boost_system%s' % env['BOOST_APPEND'])
|
|
||||||
|
|
||||||
if env['PLUGIN_LINKING'] == 'shared':
|
|
||||||
libraries.append(env['MAPNIK_NAME'])
|
|
||||||
|
|
||||||
TARGET = plugin_env.SharedLibrary('../%s' % PLUGIN_NAME,
|
|
||||||
SHLIBPREFIX='',
|
|
||||||
SHLIBSUFFIX='.input',
|
|
||||||
source=plugin_sources,
|
|
||||||
LIBS=libraries)
|
|
||||||
|
|
||||||
# if the plugin links to libmapnik ensure it is built first
|
|
||||||
Depends(TARGET, env.subst('../../../src/%s' % env['MAPNIK_LIB_NAME']))
|
|
||||||
|
|
||||||
if 'uninstall' not in COMMAND_LINE_TARGETS:
|
|
||||||
env.Install(env['MAPNIK_INPUT_PLUGINS_DEST'], TARGET)
|
|
||||||
env.Alias('install', env['MAPNIK_INPUT_PLUGINS_DEST'])
|
|
||||||
|
|
||||||
plugin_obj = {
|
|
||||||
'LIBS': libraries,
|
|
||||||
'SOURCES': plugin_sources,
|
|
||||||
}
|
|
||||||
|
|
||||||
Return('plugin_obj')
|
|
|
@ -1,66 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/datasource.hpp>
|
|
||||||
#include <mapnik/util/fs.hpp>
|
|
||||||
|
|
||||||
// std
|
|
||||||
#include <sstream>
|
|
||||||
|
|
||||||
#include "dataset_deliverer.h"
|
|
||||||
|
|
||||||
osm_dataset * dataset_deliverer::dataset = nullptr;
|
|
||||||
std::string dataset_deliverer::last_bbox = "";
|
|
||||||
std::string dataset_deliverer::last_filename = "";
|
|
||||||
|
|
||||||
osm_dataset* dataset_deliverer::load_from_file(const string& file, const string& parser)
|
|
||||||
{
|
|
||||||
// Only actually load from file if we haven't done so already
|
|
||||||
if (dataset == nullptr)
|
|
||||||
{
|
|
||||||
if (!mapnik::util::exists(file))
|
|
||||||
{
|
|
||||||
throw mapnik::datasource_exception("OSM Plugin: '" + file + "' does not exist");
|
|
||||||
}
|
|
||||||
|
|
||||||
dataset = new osm_dataset;
|
|
||||||
if (dataset->load(file.c_str(), parser) == false)
|
|
||||||
{
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
atexit(dataset_deliverer::release);
|
|
||||||
last_filename = file;
|
|
||||||
}
|
|
||||||
else if(file != last_filename)
|
|
||||||
{
|
|
||||||
dataset = new osm_dataset;
|
|
||||||
if (dataset->load(file.c_str(), parser) == false)
|
|
||||||
{
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
last_filename = file;
|
|
||||||
}
|
|
||||||
return dataset;
|
|
||||||
}
|
|
|
@ -1,47 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2011 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef DATASET_DELIVERER_H
|
|
||||||
#define DATASET_DELIVERER_H
|
|
||||||
|
|
||||||
#include "osm.h"
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
using namespace std;
|
|
||||||
|
|
||||||
class dataset_deliverer
|
|
||||||
{
|
|
||||||
private:
|
|
||||||
static osm_dataset* dataset;
|
|
||||||
static std::string last_bbox;
|
|
||||||
static std::string last_filename;
|
|
||||||
|
|
||||||
public:
|
|
||||||
static osm_dataset *load_from_file(const string&, const string&);
|
|
||||||
|
|
||||||
static void release()
|
|
||||||
{
|
|
||||||
delete dataset;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // DATASET_DELIVERER_H
|
|
|
@ -1,230 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#include "osm.h"
|
|
||||||
#include "osmparser.h"
|
|
||||||
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
|
|
||||||
#include <libxml/parser.h>
|
|
||||||
#include <iostream>
|
|
||||||
#include <fstream>
|
|
||||||
#include <sstream>
|
|
||||||
#include <string>
|
|
||||||
#include <cstring>
|
|
||||||
|
|
||||||
polygon_types osm_way::ptypes;
|
|
||||||
|
|
||||||
bool osm_dataset::load(const char* filename,std::string const& parser)
|
|
||||||
{
|
|
||||||
if (parser == "libxml2")
|
|
||||||
{
|
|
||||||
return osmparser::parse(this, filename);
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
osm_dataset::~osm_dataset()
|
|
||||||
{
|
|
||||||
clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
void osm_dataset::clear()
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(osm) << "osm_dataset: Clear";
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(osm) << "osm_dataset: -- Deleting ways";
|
|
||||||
for (unsigned int count = 0; count < ways.size(); ++count)
|
|
||||||
{
|
|
||||||
delete ways[count];
|
|
||||||
ways[count] = nullptr;
|
|
||||||
}
|
|
||||||
ways.clear();
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(osm) << "osm_dataset: -- Deleting nodes";
|
|
||||||
for (unsigned int count = 0; count < nodes.size(); ++count)
|
|
||||||
{
|
|
||||||
delete nodes[count];
|
|
||||||
nodes[count] = nullptr;
|
|
||||||
}
|
|
||||||
nodes.clear();
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(osm) << "osm_dataset: Clear done";
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string osm_dataset::to_string()
|
|
||||||
{
|
|
||||||
std::string result;
|
|
||||||
|
|
||||||
for (unsigned int count = 0; count < nodes.size(); ++count)
|
|
||||||
{
|
|
||||||
result += nodes[count]->to_string();
|
|
||||||
}
|
|
||||||
|
|
||||||
for (unsigned int count = 0; count < ways.size(); ++count)
|
|
||||||
{
|
|
||||||
result += ways[count]->to_string();
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
bounds osm_dataset::get_bounds()
|
|
||||||
{
|
|
||||||
bounds b (-180, -90, 180, 90);
|
|
||||||
for (unsigned int count = 0; count < nodes.size(); ++count)
|
|
||||||
{
|
|
||||||
if(nodes[count]->lon > b.w) b.w = nodes[count]->lon;
|
|
||||||
if(nodes[count]->lon < b.e) b.e = nodes[count]->lon;
|
|
||||||
if(nodes[count]->lat > b.s) b.s = nodes[count]->lat;
|
|
||||||
if(nodes[count]->lat < b.n) b.n = nodes[count]->lat;
|
|
||||||
}
|
|
||||||
return b;
|
|
||||||
}
|
|
||||||
|
|
||||||
osm_node* osm_dataset::next_node()
|
|
||||||
{
|
|
||||||
if (node_i != nodes.end())
|
|
||||||
{
|
|
||||||
return *(node_i++);
|
|
||||||
}
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
osm_way* osm_dataset::next_way()
|
|
||||||
{
|
|
||||||
if (way_i != ways.end())
|
|
||||||
{
|
|
||||||
return *(way_i++);
|
|
||||||
}
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
osm_item* osm_dataset::next_item()
|
|
||||||
{
|
|
||||||
osm_item* item = nullptr;
|
|
||||||
if (next_item_mode == Node)
|
|
||||||
{
|
|
||||||
item = next_node();
|
|
||||||
if (item == nullptr)
|
|
||||||
{
|
|
||||||
next_item_mode = Way;
|
|
||||||
rewind_ways();
|
|
||||||
item = next_way();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
item = next_way();
|
|
||||||
}
|
|
||||||
return item;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::set<std::string> osm_dataset::get_keys()
|
|
||||||
{
|
|
||||||
std::set<std::string> keys;
|
|
||||||
for (unsigned int count = 0; count < nodes.size(); ++count)
|
|
||||||
{
|
|
||||||
for (std::map<std::string, std::string>::iterator i = nodes[count]->keyvals.begin();
|
|
||||||
i != nodes[count]->keyvals.end(); i++)
|
|
||||||
{
|
|
||||||
keys.insert(i->first);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for (unsigned int count = 0; count < ways.size(); ++count)
|
|
||||||
{
|
|
||||||
for (std::map<std::string, std::string>::iterator i = ways[count]->keyvals.begin();
|
|
||||||
i != ways[count]->keyvals.end(); i++)
|
|
||||||
{
|
|
||||||
keys.insert(i->first);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return keys;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
std::string osm_item::to_string()
|
|
||||||
{
|
|
||||||
std::ostringstream strm;
|
|
||||||
strm << "id=" << id << std::endl << "Keyvals: " << std::endl;
|
|
||||||
|
|
||||||
for (std::map<std::string, std::string>::iterator i = keyvals.begin();
|
|
||||||
i != keyvals.end(); i++)
|
|
||||||
{
|
|
||||||
strm << "Key " << i->first << " Value " << i->second << std::endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
return strm.str();
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string osm_node::to_string()
|
|
||||||
{
|
|
||||||
std::ostringstream strm;
|
|
||||||
strm << "Node: " << osm_item::to_string() << " lat=" << lat <<" lon=" <<lon << std::endl;
|
|
||||||
return strm.str();
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string osm_way::to_string()
|
|
||||||
{
|
|
||||||
std::ostringstream strm;
|
|
||||||
strm << "Way: " << osm_item::to_string() << "Nodes in way:";
|
|
||||||
|
|
||||||
for (unsigned int count = 0; count < nodes.size(); ++count)
|
|
||||||
{
|
|
||||||
if (nodes[count] != nullptr)
|
|
||||||
{
|
|
||||||
strm << nodes[count]->id << " ";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
strm << std::endl;
|
|
||||||
return strm.str();
|
|
||||||
}
|
|
||||||
|
|
||||||
bounds osm_way::get_bounds()
|
|
||||||
{
|
|
||||||
bounds b (-180, -90, 180, 90);
|
|
||||||
|
|
||||||
for (unsigned int count = 0; count < nodes.size(); ++count)
|
|
||||||
{
|
|
||||||
if(nodes[count]->lon > b.w) b.w = nodes[count]->lon;
|
|
||||||
if(nodes[count]->lon < b.e) b.e = nodes[count]->lon;
|
|
||||||
if(nodes[count]->lat > b.s) b.s = nodes[count]->lat;
|
|
||||||
if(nodes[count]->lat < b.n) b.n = nodes[count]->lat;
|
|
||||||
}
|
|
||||||
return b;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool osm_way::is_polygon()
|
|
||||||
{
|
|
||||||
for (unsigned int count = 0; count < ptypes.ptypes.size(); ++count)
|
|
||||||
{
|
|
||||||
if (keyvals.find(ptypes.ptypes[count].first) != keyvals.end() &&
|
|
||||||
(ptypes.ptypes[count].second.empty() || keyvals[ptypes.ptypes[count].first] == ptypes.ptypes[count].second))
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
|
@ -1,136 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2011 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OSM_H
|
|
||||||
#define OSM_H
|
|
||||||
|
|
||||||
#include <mapnik/value_types.hpp>
|
|
||||||
#include <vector>
|
|
||||||
#include <string>
|
|
||||||
#include <map>
|
|
||||||
#include <set>
|
|
||||||
#include <utility>
|
|
||||||
|
|
||||||
struct bounds
|
|
||||||
{
|
|
||||||
double w, s, e, n;
|
|
||||||
bounds() { w = -180; s = -90; e = 180; n = 90; }
|
|
||||||
bounds(double w_, double s_, double e_, double n_)
|
|
||||||
{
|
|
||||||
this->w = w_;
|
|
||||||
this->s = s_;
|
|
||||||
this->e = e_;
|
|
||||||
this->n = n_;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
class polygon_types
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
std::vector<std::pair<std::string, std::string> > ptypes;
|
|
||||||
|
|
||||||
polygon_types()
|
|
||||||
{
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("water", ""));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("aeroway", ""));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("building", ""));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("natural", "wood"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("natural", "water"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("natural", "heath"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("natural", "marsh"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("military", "danger_area"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("landuse", "forest"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("landuse", "industrial"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("leisure", "park"));
|
|
||||||
ptypes.push_back(std::pair<std::string, std::string>("area", "yes"));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct osm_item
|
|
||||||
{
|
|
||||||
mapnik::value_integer id;
|
|
||||||
std::map<std::string, std::string> keyvals;
|
|
||||||
virtual std::string to_string();
|
|
||||||
virtual ~osm_item() {}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct osm_node : public osm_item
|
|
||||||
{
|
|
||||||
double lat, lon;
|
|
||||||
std::string to_string();
|
|
||||||
};
|
|
||||||
|
|
||||||
struct osm_way : public osm_item
|
|
||||||
{
|
|
||||||
std::vector<osm_node*> nodes;
|
|
||||||
std::string to_string();
|
|
||||||
bounds get_bounds();
|
|
||||||
bool is_polygon();
|
|
||||||
static polygon_types ptypes;
|
|
||||||
};
|
|
||||||
|
|
||||||
class osm_dataset
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
osm_dataset()
|
|
||||||
{
|
|
||||||
node_i = nodes.begin();
|
|
||||||
way_i = ways.begin();
|
|
||||||
next_item_mode = Node;
|
|
||||||
}
|
|
||||||
|
|
||||||
osm_dataset(const char* name)
|
|
||||||
{
|
|
||||||
node_i = nodes.begin();
|
|
||||||
way_i = ways.begin();
|
|
||||||
next_item_mode = Node;
|
|
||||||
load(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
~osm_dataset();
|
|
||||||
|
|
||||||
bool load(const char* name, std::string const& parser = "libxml2");
|
|
||||||
void clear();
|
|
||||||
void add_node(osm_node* n) { nodes.push_back(n); }
|
|
||||||
void add_way(osm_way* w) { ways.push_back(w); }
|
|
||||||
std::string to_string();
|
|
||||||
bounds get_bounds();
|
|
||||||
std::set<std::string> get_keys();
|
|
||||||
void rewind_nodes() { node_i = nodes.begin(); }
|
|
||||||
void rewind_ways() { way_i = ways.begin(); }
|
|
||||||
void rewind() { rewind_nodes(); rewind_ways(); next_item_mode = Node; }
|
|
||||||
osm_node * next_node();
|
|
||||||
osm_way * next_way();
|
|
||||||
osm_item * next_item();
|
|
||||||
bool current_item_is_node() { return next_item_mode == Node; }
|
|
||||||
bool current_item_is_way() { return next_item_mode == Way; }
|
|
||||||
|
|
||||||
private:
|
|
||||||
int next_item_mode;
|
|
||||||
enum { Node, Way };
|
|
||||||
std::vector<osm_node*>::iterator node_i;
|
|
||||||
std::vector<osm_way*>::iterator way_i;
|
|
||||||
std::vector<osm_node*> nodes;
|
|
||||||
std::vector<osm_way*> ways;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OSM_H
|
|
|
@ -1,159 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
// stl
|
|
||||||
#include <stdexcept>
|
|
||||||
#include <set>
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/geom_util.hpp>
|
|
||||||
#include <mapnik/query.hpp>
|
|
||||||
#include <mapnik/boolean.hpp>
|
|
||||||
|
|
||||||
// boost
|
|
||||||
|
|
||||||
#include "osm_datasource.hpp"
|
|
||||||
#include "osm_featureset.hpp"
|
|
||||||
#include "dataset_deliverer.h"
|
|
||||||
#include "osmtagtypes.h"
|
|
||||||
#include "osmparser.h"
|
|
||||||
|
|
||||||
using mapnik::String;
|
|
||||||
using mapnik::Double;
|
|
||||||
using mapnik::Integer;
|
|
||||||
using mapnik::datasource_exception;
|
|
||||||
using mapnik::filter_in_box;
|
|
||||||
using mapnik::filter_at_point;
|
|
||||||
using mapnik::attribute_descriptor;
|
|
||||||
|
|
||||||
DATASOURCE_PLUGIN(osm_datasource)
|
|
||||||
|
|
||||||
osm_datasource::osm_datasource(const parameters& params)
|
|
||||||
: datasource (params),
|
|
||||||
extent_(),
|
|
||||||
type_(datasource::Vector),
|
|
||||||
desc_(osm_datasource::name(), *params.get<std::string>("encoding", "utf-8"))
|
|
||||||
{
|
|
||||||
osm_data_ = nullptr;
|
|
||||||
std::string osm_filename = *params.get<std::string>("file", "");
|
|
||||||
std::string parser = *params.get<std::string>("parser", "libxml2");
|
|
||||||
std::string url = *params.get<std::string>("url", "");
|
|
||||||
std::string bbox = *params.get<std::string>("bbox", "");
|
|
||||||
|
|
||||||
// load the data
|
|
||||||
if (url != "" && bbox != "")
|
|
||||||
{
|
|
||||||
throw datasource_exception("Error loading from URL is no longer supported (removed in >= Mapnik 2.3.x");
|
|
||||||
}
|
|
||||||
else if (osm_filename != "")
|
|
||||||
{
|
|
||||||
// if we supplied a filename, load from file
|
|
||||||
if ((osm_data_ = dataset_deliverer::load_from_file(osm_filename, parser)) == nullptr)
|
|
||||||
{
|
|
||||||
std::string s("OSM Plugin: Error loading from file '");
|
|
||||||
s += osm_filename + "'";
|
|
||||||
throw datasource_exception(s);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
throw datasource_exception("OSM Plugin: Neither 'file' nor 'url' and 'bbox' specified");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
osm_tag_types tagtypes;
|
|
||||||
tagtypes.add_type("maxspeed", mapnik::Integer);
|
|
||||||
tagtypes.add_type("z_order", mapnik::Integer);
|
|
||||||
|
|
||||||
osm_data_->rewind();
|
|
||||||
|
|
||||||
// Need code to get the attributes of all the data
|
|
||||||
std::set<std::string> keys = osm_data_->get_keys();
|
|
||||||
|
|
||||||
// Add the attributes to the datasource descriptor - assume they are
|
|
||||||
// all of type String
|
|
||||||
for (auto const& key : keys)
|
|
||||||
{
|
|
||||||
desc_.add_descriptor(attribute_descriptor(key, tagtypes.get_type(key)));
|
|
||||||
}
|
|
||||||
// Get the bounds of the data and set extent_ accordingly
|
|
||||||
bounds b = osm_data_->get_bounds();
|
|
||||||
extent_ = box2d<double>(b.w,b.s,b.e,b.n);
|
|
||||||
}
|
|
||||||
|
|
||||||
osm_datasource::~osm_datasource()
|
|
||||||
{
|
|
||||||
// Do not do as is now static variable and cleaned up at exit
|
|
||||||
//delete osm_data_;
|
|
||||||
}
|
|
||||||
|
|
||||||
const char * osm_datasource::name()
|
|
||||||
{
|
|
||||||
return "osm";
|
|
||||||
}
|
|
||||||
|
|
||||||
mapnik::datasource::datasource_t osm_datasource::type() const
|
|
||||||
{
|
|
||||||
return type_;
|
|
||||||
}
|
|
||||||
|
|
||||||
layer_descriptor osm_datasource::get_descriptor() const
|
|
||||||
{
|
|
||||||
return desc_;
|
|
||||||
}
|
|
||||||
|
|
||||||
featureset_ptr osm_datasource::features(const query& q) const
|
|
||||||
{
|
|
||||||
filter_in_box filter(q.get_bbox());
|
|
||||||
// so we need to filter osm features by bbox here...
|
|
||||||
|
|
||||||
return std::make_shared<osm_featureset<filter_in_box> >(filter,
|
|
||||||
osm_data_,
|
|
||||||
q.property_names(),
|
|
||||||
desc_.get_encoding());
|
|
||||||
}
|
|
||||||
|
|
||||||
featureset_ptr osm_datasource::features_at_point(coord2d const& pt, double tol) const
|
|
||||||
{
|
|
||||||
filter_at_point filter(pt);
|
|
||||||
// collect all attribute names
|
|
||||||
std::set<std::string> names;
|
|
||||||
for (auto const& elem : desc_.get_descriptors())
|
|
||||||
{
|
|
||||||
names.insert(elem.get_name());
|
|
||||||
}
|
|
||||||
return std::make_shared<osm_featureset<filter_at_point> >(filter,
|
|
||||||
osm_data_,
|
|
||||||
names,
|
|
||||||
desc_.get_encoding());
|
|
||||||
}
|
|
||||||
|
|
||||||
box2d<double> osm_datasource::envelope() const
|
|
||||||
{
|
|
||||||
return extent_;
|
|
||||||
}
|
|
||||||
|
|
||||||
boost::optional<mapnik::datasource_geometry_t> osm_datasource::get_geometry_type() const
|
|
||||||
{
|
|
||||||
return boost::optional<mapnik::datasource_geometry_t>(mapnik::datasource_geometry_t::Collection);
|
|
||||||
}
|
|
|
@ -1,73 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OSM_DATASOURCE_HPP
|
|
||||||
#define OSM_DATASOURCE_HPP
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/datasource.hpp>
|
|
||||||
#include <mapnik/params.hpp>
|
|
||||||
#include <mapnik/query.hpp>
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/box2d.hpp>
|
|
||||||
#include <mapnik/coord.hpp>
|
|
||||||
#include <mapnik/feature_layer_desc.hpp>
|
|
||||||
|
|
||||||
// boost
|
|
||||||
#include <boost/optional.hpp>
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
// stl
|
|
||||||
#include <vector>
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
#include "osm.h"
|
|
||||||
|
|
||||||
using mapnik::datasource;
|
|
||||||
using mapnik::parameters;
|
|
||||||
using mapnik::query;
|
|
||||||
using mapnik::featureset_ptr;
|
|
||||||
using mapnik::layer_descriptor;
|
|
||||||
using mapnik::coord2d;
|
|
||||||
using mapnik::box2d;
|
|
||||||
|
|
||||||
class osm_datasource : public datasource
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
osm_datasource(const parameters& params);
|
|
||||||
virtual ~osm_datasource();
|
|
||||||
mapnik::datasource::datasource_t type() const;
|
|
||||||
static const char * name();
|
|
||||||
featureset_ptr features(const query& q) const;
|
|
||||||
featureset_ptr features_at_point(coord2d const& pt, double tol = 0) const;
|
|
||||||
box2d<double> envelope() const;
|
|
||||||
boost::optional<mapnik::datasource_geometry_t> get_geometry_type() const;
|
|
||||||
layer_descriptor get_descriptor() const;
|
|
||||||
|
|
||||||
private:
|
|
||||||
box2d<double> extent_;
|
|
||||||
osm_dataset* osm_data_;
|
|
||||||
mapnik::datasource::datasource_t type_;
|
|
||||||
layer_descriptor desc_;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OSM_DATASOURCE_HPP
|
|
|
@ -1,132 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/make_unique.hpp>
|
|
||||||
#include <mapnik/geometry.hpp>
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/feature_factory.hpp>
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/unicode.hpp>
|
|
||||||
#include <mapnik/geometry_correct.hpp>
|
|
||||||
|
|
||||||
#include "osm_featureset.hpp"
|
|
||||||
|
|
||||||
using mapnik::feature_ptr;
|
|
||||||
using mapnik::feature_factory;
|
|
||||||
|
|
||||||
template <typename filterT>
|
|
||||||
osm_featureset<filterT>::osm_featureset(const filterT& filter,
|
|
||||||
osm_dataset* dataset,
|
|
||||||
const std::set<std::string>&
|
|
||||||
attribute_names,
|
|
||||||
std::string const& encoding)
|
|
||||||
: filter_(filter),
|
|
||||||
query_ext_(),
|
|
||||||
tr_(new transcoder(encoding)),
|
|
||||||
dataset_ (dataset),
|
|
||||||
attribute_names_ (attribute_names),
|
|
||||||
ctx_(std::make_shared<mapnik::context_type>())
|
|
||||||
{
|
|
||||||
dataset_->rewind();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <typename filterT>
|
|
||||||
feature_ptr osm_featureset<filterT>::next()
|
|
||||||
{
|
|
||||||
feature_ptr feature;
|
|
||||||
|
|
||||||
osm_item* cur_item = dataset_->next_item();
|
|
||||||
if (!cur_item) return feature_ptr();
|
|
||||||
if (dataset_->current_item_is_node())
|
|
||||||
{
|
|
||||||
feature = feature_factory::create(ctx_, cur_item->id);
|
|
||||||
double lat = static_cast<osm_node*>(cur_item)->lat;
|
|
||||||
double lon = static_cast<osm_node*>(cur_item)->lon;
|
|
||||||
feature->set_geometry(mapnik::geometry::point<double>(lon,lat));
|
|
||||||
}
|
|
||||||
else if (dataset_->current_item_is_way())
|
|
||||||
{
|
|
||||||
// Loop until we find a feature which passes the filter
|
|
||||||
while (cur_item)
|
|
||||||
{
|
|
||||||
bounds b = static_cast<osm_way*>(cur_item)->get_bounds();
|
|
||||||
if (filter_.pass(box2d<double>(b.w, b.s, b.e, b.n))
|
|
||||||
&&
|
|
||||||
static_cast<osm_way*>(cur_item)->nodes.size()) break;
|
|
||||||
cur_item = dataset_->next_item();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!cur_item) return feature_ptr();
|
|
||||||
feature = feature_factory::create(ctx_, cur_item->id);
|
|
||||||
if (static_cast<osm_way*>(cur_item)->is_polygon())
|
|
||||||
{
|
|
||||||
mapnik::geometry::linear_ring<double> ring;
|
|
||||||
for (unsigned int count = 0;
|
|
||||||
count < static_cast<osm_way*>(cur_item)->nodes.size();
|
|
||||||
count++)
|
|
||||||
{
|
|
||||||
ring.add_coord(static_cast<osm_way*>(cur_item)->nodes[count]->lon,
|
|
||||||
static_cast<osm_way*>(cur_item)->nodes[count]->lat);
|
|
||||||
}
|
|
||||||
mapnik::geometry::polygon<double> geom;
|
|
||||||
geom.set_exterior_ring(std::move(ring));
|
|
||||||
mapnik::geometry::correct(geom);
|
|
||||||
feature->set_geometry(std::move(geom));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mapnik::geometry::line_string<double> geom;
|
|
||||||
for (unsigned int count = 0;
|
|
||||||
count < static_cast<osm_way*>(cur_item)->nodes.size();
|
|
||||||
count++)
|
|
||||||
{
|
|
||||||
geom.add_coord(static_cast<osm_way*>(cur_item)->nodes[count]->lon,
|
|
||||||
static_cast<osm_way*>(cur_item)->nodes[count]->lat);
|
|
||||||
}
|
|
||||||
feature->set_geometry(std::move(geom));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_ERROR(osm_featureset) << "Current item is neither node nor way.\n";
|
|
||||||
}
|
|
||||||
|
|
||||||
std::set<std::string>::const_iterator itr = attribute_names_.begin();
|
|
||||||
std::set<std::string>::const_iterator end = attribute_names_.end();
|
|
||||||
std::map<std::string,std::string>::iterator end_keyvals = cur_item->keyvals.end();
|
|
||||||
for (; itr != end; itr++)
|
|
||||||
{
|
|
||||||
std::map<std::string,std::string>::iterator i = cur_item->keyvals.find(*itr);
|
|
||||||
if (i != end_keyvals)
|
|
||||||
{
|
|
||||||
feature->put_new(i->first, tr_->transcode(i->second.c_str()));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return feature;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <typename filterT>
|
|
||||||
osm_featureset<filterT>::~osm_featureset() {}
|
|
||||||
|
|
||||||
template class osm_featureset<mapnik::filter_in_box>;
|
|
||||||
template class osm_featureset<mapnik::filter_at_point>;
|
|
|
@ -1,72 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OSM_FS_HH
|
|
||||||
#define OSM_FS_HH
|
|
||||||
|
|
||||||
// stl
|
|
||||||
#include <set>
|
|
||||||
|
|
||||||
// boost
|
|
||||||
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/geom_util.hpp>
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/query.hpp>
|
|
||||||
#include <mapnik/unicode.hpp>
|
|
||||||
#include <mapnik/datasource.hpp>
|
|
||||||
|
|
||||||
#include "osm.h"
|
|
||||||
|
|
||||||
using mapnik::Featureset;
|
|
||||||
using mapnik::box2d;
|
|
||||||
using mapnik::feature_ptr;
|
|
||||||
using mapnik::transcoder;
|
|
||||||
|
|
||||||
template <typename filterT>
|
|
||||||
class osm_featureset : public Featureset
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
osm_featureset(const filterT& filter,
|
|
||||||
osm_dataset* dataset,
|
|
||||||
const std::set<std::string>& attribute_names,
|
|
||||||
std::string const& encoding);
|
|
||||||
virtual ~osm_featureset();
|
|
||||||
feature_ptr next();
|
|
||||||
|
|
||||||
private:
|
|
||||||
filterT filter_;
|
|
||||||
box2d<double> query_ext_;
|
|
||||||
const std::unique_ptr<transcoder> tr_;
|
|
||||||
std::vector<int> attr_ids_;
|
|
||||||
mutable box2d<double> feature_ext_;
|
|
||||||
mutable int total_geom_size;
|
|
||||||
osm_dataset *dataset_;
|
|
||||||
std::set<std::string> attribute_names_;
|
|
||||||
mapnik::context_ptr ctx_;
|
|
||||||
|
|
||||||
osm_featureset(const osm_featureset&);
|
|
||||||
const osm_featureset& operator=(const osm_featureset&);
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OSM_FS_HH
|
|
|
@ -1,150 +0,0 @@
|
||||||
// much of this is based on osm2pgsql
|
|
||||||
|
|
||||||
#include "osmparser.h"
|
|
||||||
#include "osm.h"
|
|
||||||
#include <string>
|
|
||||||
#include <cassert>
|
|
||||||
#include <mapnik/util/conversions.hpp>
|
|
||||||
|
|
||||||
osm_item* osmparser::cur_item=nullptr;
|
|
||||||
mapnik::value_integer osmparser::curID=0;
|
|
||||||
bool osmparser::in_node=false, osmparser::in_way=false;
|
|
||||||
osm_dataset* osmparser::components=nullptr;
|
|
||||||
std::string osmparser::error="";
|
|
||||||
std::map<mapnik::value_integer,osm_node*> osmparser::tmp_node_store=std::map<mapnik::value_integer,osm_node*>();
|
|
||||||
|
|
||||||
void osmparser::processNode(xmlTextReaderPtr reader)
|
|
||||||
{
|
|
||||||
xmlChar *name = xmlTextReaderName(reader);
|
|
||||||
if(name==nullptr)
|
|
||||||
name=xmlStrdup(BAD_CAST "--");
|
|
||||||
|
|
||||||
switch(xmlTextReaderNodeType(reader))
|
|
||||||
{
|
|
||||||
case XML_READER_TYPE_ELEMENT:
|
|
||||||
startElement(reader,name);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case XML_READER_TYPE_END_ELEMENT:
|
|
||||||
endElement(name);
|
|
||||||
}
|
|
||||||
xmlFree(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
void osmparser::startElement(xmlTextReaderPtr reader, const xmlChar *name)
|
|
||||||
{
|
|
||||||
std::string tags;
|
|
||||||
xmlChar *xid, *xlat, *xlon, *xk, *xv;
|
|
||||||
|
|
||||||
if(xmlStrEqual(name,BAD_CAST "node"))
|
|
||||||
{
|
|
||||||
curID = 0;
|
|
||||||
in_node = true;
|
|
||||||
osm_node *node=new osm_node;
|
|
||||||
xlat=xmlTextReaderGetAttribute(reader,BAD_CAST "lat");
|
|
||||||
xlon=xmlTextReaderGetAttribute(reader,BAD_CAST "lon");
|
|
||||||
xid=xmlTextReaderGetAttribute(reader,BAD_CAST "id");
|
|
||||||
assert(xlat);
|
|
||||||
assert(xlon);
|
|
||||||
assert(xid);
|
|
||||||
node->lat=atof((char*)xlat);
|
|
||||||
node->lon=atof((char*)xlon);
|
|
||||||
mapnik::util::string2int((char *)xid, node->id);
|
|
||||||
cur_item = node;
|
|
||||||
tmp_node_store[node->id] = node;
|
|
||||||
xmlFree(xid);
|
|
||||||
xmlFree(xlon);
|
|
||||||
xmlFree(xlat);
|
|
||||||
}
|
|
||||||
else if (xmlStrEqual(name,BAD_CAST "way"))
|
|
||||||
{
|
|
||||||
curID=0;
|
|
||||||
in_way = true;
|
|
||||||
osm_way *way=new osm_way;
|
|
||||||
xid=xmlTextReaderGetAttribute(reader,BAD_CAST "id");
|
|
||||||
assert(xid);
|
|
||||||
mapnik::util::string2int((char *)xid, way->id);
|
|
||||||
cur_item = way;
|
|
||||||
xmlFree(xid);
|
|
||||||
}
|
|
||||||
else if (xmlStrEqual(name,BAD_CAST "nd"))
|
|
||||||
{
|
|
||||||
xid=xmlTextReaderGetAttribute(reader,BAD_CAST "ref");
|
|
||||||
assert(xid);
|
|
||||||
mapnik::value_integer ndid;
|
|
||||||
mapnik::util::string2int((char *)xid, ndid);
|
|
||||||
if(tmp_node_store.find(ndid)!=tmp_node_store.end())
|
|
||||||
{
|
|
||||||
(static_cast<osm_way*>(cur_item))->nodes.push_back
|
|
||||||
(tmp_node_store[ndid]);
|
|
||||||
}
|
|
||||||
xmlFree(xid);
|
|
||||||
}
|
|
||||||
else if (xmlStrEqual(name,BAD_CAST "tag"))
|
|
||||||
{
|
|
||||||
std::string key="", value="";
|
|
||||||
xk = xmlTextReaderGetAttribute(reader,BAD_CAST "k");
|
|
||||||
xv = xmlTextReaderGetAttribute(reader,BAD_CAST "v");
|
|
||||||
assert(xk);
|
|
||||||
assert(xv);
|
|
||||||
cur_item->keyvals[(char*)xk] = (char*)xv;
|
|
||||||
xmlFree(xk);
|
|
||||||
xmlFree(xv);
|
|
||||||
}
|
|
||||||
if (xmlTextReaderIsEmptyElement(reader))
|
|
||||||
{
|
|
||||||
// Fake endElement for empty nodes
|
|
||||||
endElement(name);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void osmparser::endElement(const xmlChar* name)
|
|
||||||
{
|
|
||||||
if(xmlStrEqual(name,BAD_CAST "node"))
|
|
||||||
{
|
|
||||||
in_node = false;
|
|
||||||
components->add_node(static_cast<osm_node*>(cur_item));
|
|
||||||
}
|
|
||||||
else if(xmlStrEqual(name,BAD_CAST "way"))
|
|
||||||
{
|
|
||||||
in_way = false;
|
|
||||||
components->add_way(static_cast<osm_way*>(cur_item));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool osmparser::parse(osm_dataset *ds, const char* filename)
|
|
||||||
{
|
|
||||||
components=ds;
|
|
||||||
xmlTextReaderPtr reader = xmlNewTextReaderFilename(filename);
|
|
||||||
int ret=do_parse(reader);
|
|
||||||
xmlFreeTextReader(reader);
|
|
||||||
return (ret==0) ? true:false;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool osmparser::parse(osm_dataset *ds,char* data, int nbytes)
|
|
||||||
{
|
|
||||||
// from cocoasamurai.blogspot.com/2008/10/getting-some-xml-love-with-
|
|
||||||
// libxml2.html, converted from Objective-C to straight C
|
|
||||||
|
|
||||||
components=ds;
|
|
||||||
xmlTextReaderPtr reader = xmlReaderForMemory(data,nbytes,nullptr,nullptr,0);
|
|
||||||
int ret=do_parse(reader);
|
|
||||||
xmlFreeTextReader(reader);
|
|
||||||
return (ret==0) ? true:false;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int osmparser::do_parse(xmlTextReaderPtr reader)
|
|
||||||
{
|
|
||||||
int ret=-1;
|
|
||||||
if(reader!=nullptr)
|
|
||||||
{
|
|
||||||
ret = xmlTextReaderRead(reader);
|
|
||||||
while(ret==1)
|
|
||||||
{
|
|
||||||
processNode(reader);
|
|
||||||
ret=xmlTextReaderRead(reader);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return ret;
|
|
||||||
}
|
|
|
@ -1,54 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2011 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OSMPARSER_H
|
|
||||||
#define OSMPARSER_H
|
|
||||||
|
|
||||||
#include <mapnik/value_types.hpp>
|
|
||||||
#include <libxml/xmlreader.h>
|
|
||||||
#include <cstdio>
|
|
||||||
#include <cstdlib>
|
|
||||||
#include <string>
|
|
||||||
#include "osm.h"
|
|
||||||
#include <map>
|
|
||||||
|
|
||||||
class osmparser
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
static void processNode(xmlTextReaderPtr reader);
|
|
||||||
static void startElement(xmlTextReaderPtr reader, const xmlChar* name);
|
|
||||||
static void endElement(const xmlChar* name);
|
|
||||||
static bool parse(osm_dataset* ds, const char* filename);
|
|
||||||
static bool parse(osm_dataset* ds, char* data, int nbytes);
|
|
||||||
|
|
||||||
private:
|
|
||||||
static osm_item *cur_item;
|
|
||||||
static mapnik::value_integer curID;
|
|
||||||
static bool in_node, in_way;
|
|
||||||
static osm_dataset* components;
|
|
||||||
static std::string error;
|
|
||||||
static std::map<mapnik::value_integer, osm_node*> tmp_node_store;
|
|
||||||
|
|
||||||
static int do_parse(xmlTextReaderPtr);
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OSMPARSER_H
|
|
|
@ -1,50 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2011 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef OSMTAGTYPES_H
|
|
||||||
#define OSMTAGTYPES_H
|
|
||||||
|
|
||||||
// osmtagtypes.h
|
|
||||||
// for finding the types of particular tags
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/feature_layer_desc.hpp>
|
|
||||||
|
|
||||||
class osm_tag_types
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
void add_type(std::string tag, mapnik::eAttributeType type)
|
|
||||||
{
|
|
||||||
types[tag] = type;
|
|
||||||
}
|
|
||||||
|
|
||||||
mapnik::eAttributeType get_type(std::string tag)
|
|
||||||
{
|
|
||||||
std::map<std::string, mapnik::eAttributeType>::iterator i = types.find(tag);
|
|
||||||
return (i == types.end()) ? mapnik::String : i->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
std::map<std::string, mapnik::eAttributeType> types;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // OSMTAGTYPES_H
|
|
|
@ -1,71 +0,0 @@
|
||||||
#
|
|
||||||
# This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
#
|
|
||||||
# Copyright (C) 2015 Artem Pavlenko
|
|
||||||
#
|
|
||||||
# Mapnik is free software; you can redistribute it and/or
|
|
||||||
# modify it under the terms of the GNU Lesser General Public
|
|
||||||
# License as published by the Free Software Foundation; either
|
|
||||||
# version 2.1 of the License, or (at your option) any later version.
|
|
||||||
#
|
|
||||||
# This library is distributed in the hope that it will be useful,
|
|
||||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
# Lesser General Public License for more details.
|
|
||||||
#
|
|
||||||
# You should have received a copy of the GNU Lesser General Public
|
|
||||||
# License along with this library; if not, write to the Free Software
|
|
||||||
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
#
|
|
||||||
#
|
|
||||||
|
|
||||||
Import ('plugin_base')
|
|
||||||
Import ('env')
|
|
||||||
|
|
||||||
PLUGIN_NAME = 'rasterlite'
|
|
||||||
|
|
||||||
plugin_env = plugin_base.Clone()
|
|
||||||
|
|
||||||
plugin_sources = Split(
|
|
||||||
"""
|
|
||||||
%(PLUGIN_NAME)s_datasource.cpp
|
|
||||||
%(PLUGIN_NAME)s_featureset.cpp
|
|
||||||
""" % locals()
|
|
||||||
)
|
|
||||||
|
|
||||||
# Link Library to Dependencies
|
|
||||||
libraries = [env['PLUGINS']['rasterlite']['lib']]
|
|
||||||
libraries.append(env['ICU_LIB_NAME'])
|
|
||||||
libraries.append('boost_system%s' % env['BOOST_APPEND'])
|
|
||||||
|
|
||||||
if env['RUNTIME_LINK'] == 'static':
|
|
||||||
libraries.append('geotiff')
|
|
||||||
libraries.append('spatialite')
|
|
||||||
libraries.append('sqlite3')
|
|
||||||
libraries.append('geos_c')
|
|
||||||
libraries.append('geos')
|
|
||||||
libraries.append('proj')
|
|
||||||
libraries.append('z')
|
|
||||||
|
|
||||||
if env['PLUGIN_LINKING'] == 'shared':
|
|
||||||
libraries.append(env['MAPNIK_NAME'])
|
|
||||||
|
|
||||||
TARGET = plugin_env.SharedLibrary('../%s' % PLUGIN_NAME,
|
|
||||||
SHLIBPREFIX='',
|
|
||||||
SHLIBSUFFIX='.input',
|
|
||||||
source=plugin_sources,
|
|
||||||
LIBS=libraries)
|
|
||||||
|
|
||||||
# if the plugin links to libmapnik ensure it is built first
|
|
||||||
Depends(TARGET, env.subst('../../../src/%s' % env['MAPNIK_LIB_NAME']))
|
|
||||||
|
|
||||||
if 'uninstall' not in COMMAND_LINE_TARGETS:
|
|
||||||
env.Install(env['MAPNIK_INPUT_PLUGINS_DEST'], TARGET)
|
|
||||||
env.Alias('install', env['MAPNIK_INPUT_PLUGINS_DEST'])
|
|
||||||
|
|
||||||
plugin_obj = {
|
|
||||||
'LIBS': libraries,
|
|
||||||
'SOURCES': plugin_sources,
|
|
||||||
}
|
|
||||||
|
|
||||||
Return('plugin_obj')
|
|
|
@ -1,191 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#include "rasterlite_datasource.hpp"
|
|
||||||
#include "rasterlite_featureset.hpp"
|
|
||||||
|
|
||||||
// boost
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/util/fs.hpp>
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/boolean.hpp>
|
|
||||||
#include <mapnik/geom_util.hpp>
|
|
||||||
|
|
||||||
using mapnik::datasource;
|
|
||||||
using mapnik::parameters;
|
|
||||||
|
|
||||||
DATASOURCE_PLUGIN(rasterlite_datasource)
|
|
||||||
|
|
||||||
using mapnik::box2d;
|
|
||||||
using mapnik::coord2d;
|
|
||||||
using mapnik::query;
|
|
||||||
using mapnik::featureset_ptr;
|
|
||||||
using mapnik::layer_descriptor;
|
|
||||||
using mapnik::datasource_exception;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Opens a GDALDataset and returns a pointer to it.
|
|
||||||
* Caller is responsible for calling GDALClose on it
|
|
||||||
*/
|
|
||||||
inline void* rasterlite_datasource::open_dataset() const
|
|
||||||
{
|
|
||||||
void* dataset = rasterliteOpen (dataset_name_.c_str(), table_name_.c_str());
|
|
||||||
|
|
||||||
if (! dataset)
|
|
||||||
{
|
|
||||||
throw datasource_exception("Rasterlite Plugin: Error opening dataset");
|
|
||||||
}
|
|
||||||
|
|
||||||
if (rasterliteIsError (dataset))
|
|
||||||
{
|
|
||||||
std::string error (rasterliteGetLastError(dataset));
|
|
||||||
|
|
||||||
rasterliteClose (dataset);
|
|
||||||
|
|
||||||
throw datasource_exception(error);
|
|
||||||
}
|
|
||||||
|
|
||||||
return dataset;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
rasterlite_datasource::rasterlite_datasource(parameters const& params)
|
|
||||||
: datasource(params),
|
|
||||||
desc_(rasterlite_datasource::name(),"utf-8")
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: Initializing...";
|
|
||||||
|
|
||||||
boost::optional<std::string> file = params.get<std::string>("file");
|
|
||||||
if (!file) throw datasource_exception("missing <file> parameter");
|
|
||||||
|
|
||||||
boost::optional<std::string> table = params.get<std::string>("table");
|
|
||||||
if (!table) throw datasource_exception("missing <table> parameter");
|
|
||||||
|
|
||||||
table_name_ = *table;
|
|
||||||
|
|
||||||
boost::optional<std::string> base = params.get<std::string>("base");
|
|
||||||
if (base)
|
|
||||||
dataset_name_ = *base + "/" + *file;
|
|
||||||
else
|
|
||||||
dataset_name_ = *file;
|
|
||||||
|
|
||||||
if (!mapnik::util::exists(dataset_name_)) throw datasource_exception(dataset_name_ + " does not exist");
|
|
||||||
|
|
||||||
void *dataset = open_dataset();
|
|
||||||
|
|
||||||
double x0, y0, x1, y1;
|
|
||||||
if (rasterliteGetExtent (dataset, &x0, &y0, &x1, &y1) != RASTERLITE_OK)
|
|
||||||
{
|
|
||||||
std::string error (rasterliteGetLastError(dataset));
|
|
||||||
|
|
||||||
rasterliteClose (dataset);
|
|
||||||
|
|
||||||
throw datasource_exception(error);
|
|
||||||
}
|
|
||||||
|
|
||||||
extent_.init(x0,y0,x1,y1);
|
|
||||||
|
|
||||||
#ifdef MAPNIK_LOG
|
|
||||||
int srid, auth_srid;
|
|
||||||
const char *auth_name;
|
|
||||||
const char *ref_sys_name;
|
|
||||||
const char *proj4text;
|
|
||||||
|
|
||||||
int tile_count;
|
|
||||||
double pixel_x_size, pixel_y_size;
|
|
||||||
int levels = rasterliteGetLevels (dataset);
|
|
||||||
|
|
||||||
if (rasterliteGetSrid(dataset, &srid, &auth_name, &auth_srid, &ref_sys_name, &proj4text) != RASTERLITE_OK)
|
|
||||||
{
|
|
||||||
std::string error (rasterliteGetLastError(dataset));
|
|
||||||
|
|
||||||
rasterliteClose (dataset);
|
|
||||||
|
|
||||||
throw datasource_exception(error);
|
|
||||||
}
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: Data Source=" << rasterliteGetTablePrefix(dataset);
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: SRID=" << srid;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: Authority=" << auth_name;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: AuthSRID=" << auth_srid;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: RefSys Name=" << ref_sys_name;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: Proj4Text=" << proj4text;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: Extent=" << x0 << "," << y0 << " " << x1 << "," << y1 << ")";
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: Levels=" << levels;
|
|
||||||
|
|
||||||
for (int i = 0; i < levels; i++)
|
|
||||||
{
|
|
||||||
if (rasterliteGetResolution(dataset, i, &pixel_x_size, &pixel_y_size, &tile_count) == RASTERLITE_OK)
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_datasource: Level=" << i
|
|
||||||
<< " x=" << pixel_x_size
|
|
||||||
<< " y=" << pixel_y_size
|
|
||||||
<< " tiles=" << tile_count;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
rasterliteClose(dataset);
|
|
||||||
}
|
|
||||||
|
|
||||||
rasterlite_datasource::~rasterlite_datasource()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
const char * rasterlite_datasource::name()
|
|
||||||
{
|
|
||||||
return "rasterlite";
|
|
||||||
}
|
|
||||||
|
|
||||||
mapnik::datasource::datasource_t rasterlite_datasource::type() const
|
|
||||||
{
|
|
||||||
return datasource::Raster;
|
|
||||||
}
|
|
||||||
|
|
||||||
box2d<double> rasterlite_datasource::envelope() const
|
|
||||||
{
|
|
||||||
return extent_;
|
|
||||||
}
|
|
||||||
|
|
||||||
boost::optional<mapnik::datasource_geometry_t> rasterlite_datasource::get_geometry_type() const
|
|
||||||
{
|
|
||||||
return boost::optional<mapnik::datasource_geometry_t>();
|
|
||||||
}
|
|
||||||
|
|
||||||
layer_descriptor rasterlite_datasource::get_descriptor() const
|
|
||||||
{
|
|
||||||
return desc_;
|
|
||||||
}
|
|
||||||
|
|
||||||
featureset_ptr rasterlite_datasource::features(query const& q) const
|
|
||||||
{
|
|
||||||
rasterlite_query gq = q;
|
|
||||||
return std::make_shared<rasterlite_featureset>(open_dataset(), gq);
|
|
||||||
}
|
|
||||||
|
|
||||||
featureset_ptr rasterlite_datasource::features_at_point(coord2d const& pt, double tol) const
|
|
||||||
{
|
|
||||||
rasterlite_query gq = pt;
|
|
||||||
return std::make_shared<rasterlite_featureset>(open_dataset(), gq);
|
|
||||||
}
|
|
|
@ -1,66 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef RASTERLITE_DATASOURCE_HPP
|
|
||||||
#define RASTERLITE_DATASOURCE_HPP
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/datasource.hpp>
|
|
||||||
#include <mapnik/params.hpp>
|
|
||||||
#include <mapnik/query.hpp>
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/box2d.hpp>
|
|
||||||
#include <mapnik/coord.hpp>
|
|
||||||
#include <mapnik/feature_layer_desc.hpp>
|
|
||||||
|
|
||||||
// boost
|
|
||||||
#include <boost/optional.hpp>
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
// stl
|
|
||||||
#include <vector>
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
#include "rasterlite_include.hpp"
|
|
||||||
|
|
||||||
class rasterlite_datasource : public mapnik::datasource
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
rasterlite_datasource(mapnik::parameters const& params);
|
|
||||||
virtual ~rasterlite_datasource ();
|
|
||||||
mapnik::datasource::datasource_t type() const;
|
|
||||||
static const char * name();
|
|
||||||
mapnik::featureset_ptr features(mapnik::query const& q) const;
|
|
||||||
mapnik::featureset_ptr features_at_point(mapnik::coord2d const& pt, double tol = 0) const;
|
|
||||||
mapnik::box2d<double> envelope() const;
|
|
||||||
boost::optional<mapnik::datasource_geometry_t> get_geometry_type() const;
|
|
||||||
mapnik::layer_descriptor get_descriptor() const;
|
|
||||||
|
|
||||||
private:
|
|
||||||
void* open_dataset() const;
|
|
||||||
mapnik::box2d<double> extent_;
|
|
||||||
std::string dataset_name_;
|
|
||||||
std::string table_name_;
|
|
||||||
mapnik::layer_descriptor desc_;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // RASTERLITE_DATASOURCE_HPP
|
|
|
@ -1,136 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#include "rasterlite_featureset.hpp"
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/debug.hpp>
|
|
||||||
#include <mapnik/image.hpp>
|
|
||||||
#include <mapnik/image_util.hpp>
|
|
||||||
#include <mapnik/query.hpp>
|
|
||||||
#include <mapnik/raster.hpp>
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/feature_factory.hpp>
|
|
||||||
|
|
||||||
#include <cstring>
|
|
||||||
|
|
||||||
using mapnik::coord2d;
|
|
||||||
using mapnik::box2d;
|
|
||||||
using mapnik::feature_ptr;
|
|
||||||
using mapnik::query;
|
|
||||||
using mapnik::feature_factory;
|
|
||||||
|
|
||||||
|
|
||||||
rasterlite_featureset::rasterlite_featureset(void* dataset,
|
|
||||||
rasterlite_query q)
|
|
||||||
: dataset_(dataset),
|
|
||||||
gquery_(q),
|
|
||||||
first_(true),
|
|
||||||
ctx_(std::make_shared<mapnik::context_type>())
|
|
||||||
{
|
|
||||||
rasterliteSetBackgroundColor(dataset_, 255, 0, 255);
|
|
||||||
rasterliteSetTransparentColor(dataset_, 255, 0, 255);
|
|
||||||
}
|
|
||||||
|
|
||||||
rasterlite_featureset::~rasterlite_featureset()
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Closing";
|
|
||||||
|
|
||||||
rasterliteClose(dataset_);
|
|
||||||
}
|
|
||||||
|
|
||||||
feature_ptr rasterlite_featureset::next()
|
|
||||||
{
|
|
||||||
if (first_)
|
|
||||||
{
|
|
||||||
first_ = false;
|
|
||||||
MAPNIK_LOG_DEBUG(gdal) << "rasterlite_featureset: Next feature in Dataset=" << &dataset_;
|
|
||||||
return mapnik::util::apply_visitor(query_dispatch(*this), gquery_);
|
|
||||||
}
|
|
||||||
return feature_ptr();
|
|
||||||
}
|
|
||||||
|
|
||||||
feature_ptr rasterlite_featureset::get_feature(mapnik::query const& q)
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Running get_feature";
|
|
||||||
|
|
||||||
feature_ptr feature(feature_factory::create(ctx_,1));
|
|
||||||
|
|
||||||
double x0, y0, x1, y1;
|
|
||||||
rasterliteGetExtent (dataset_, &x0, &y0, &x1, &y1);
|
|
||||||
|
|
||||||
box2d<double> raster_extent(x0, y0, x1, y1);
|
|
||||||
box2d<double> intersect = raster_extent.intersect(q.get_bbox());
|
|
||||||
|
|
||||||
const int width = static_cast<int>(std::get<0>(q.resolution()) * intersect.width() + 0.5);
|
|
||||||
const int height = static_cast<int>(std::get<0>(q.resolution()) * intersect.height() + 0.5);
|
|
||||||
|
|
||||||
const double pixel_size = (intersect.width() >= intersect.height()) ?
|
|
||||||
(intersect.width() / (double) width) : (intersect.height() / (double) height);
|
|
||||||
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Raster extent=" << raster_extent;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: View extent=" << q.get_bbox();
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Intersect extent=" << intersect;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Query resolution=" << std::get<0>(q.resolution()) << "," << std::get<1>(q.resolution());
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Size=" << width << " " << height;
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Pixel Size=" << pixel_size;
|
|
||||||
|
|
||||||
if (width > 0 && height > 0)
|
|
||||||
{
|
|
||||||
int size = 0;
|
|
||||||
void* raster = 0;
|
|
||||||
|
|
||||||
if (rasterliteGetRawImageByRect(dataset_,
|
|
||||||
intersect.minx(),
|
|
||||||
intersect.miny(),
|
|
||||||
intersect.maxx(),
|
|
||||||
intersect.maxy(),
|
|
||||||
pixel_size,
|
|
||||||
width,
|
|
||||||
height,
|
|
||||||
GAIA_RGBA_ARRAY,
|
|
||||||
&raster,
|
|
||||||
&size) == RASTERLITE_OK)
|
|
||||||
{
|
|
||||||
if (size > 0)
|
|
||||||
{
|
|
||||||
mapnik::image_rgba8 image(width,height);
|
|
||||||
unsigned char* raster_data = static_cast<unsigned char*>(raster);
|
|
||||||
std::memcpy(image.bytes(), raster_data, size);
|
|
||||||
feature->set_raster(std::make_shared<mapnik::raster>(intersect, std::move(image), 1.0));
|
|
||||||
MAPNIK_LOG_DEBUG(rasterlite) << "rasterlite_featureset: Done";
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
MAPNIK_LOG_ERROR(rasterlite) << "Rasterlite Plugin: Error " << rasterliteGetLastError (dataset_);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return feature;
|
|
||||||
}
|
|
||||||
return feature_ptr();
|
|
||||||
}
|
|
||||||
|
|
||||||
feature_ptr rasterlite_featureset::get_feature_at_point(mapnik::coord2d const& pt)
|
|
||||||
{
|
|
||||||
return feature_ptr();
|
|
||||||
}
|
|
|
@ -1,71 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef RASTERLITE_FEATURESET_HPP
|
|
||||||
#define RASTERLITE_FEATURESET_HPP
|
|
||||||
|
|
||||||
// mapnik
|
|
||||||
#include <mapnik/feature.hpp>
|
|
||||||
#include <mapnik/query.hpp>
|
|
||||||
#include <mapnik/datasource.hpp>
|
|
||||||
#include <mapnik/util/variant.hpp>
|
|
||||||
|
|
||||||
#include "rasterlite_include.hpp"
|
|
||||||
|
|
||||||
using rasterlite_query = mapnik::util::variant<mapnik::query,mapnik::coord2d>;
|
|
||||||
|
|
||||||
class rasterlite_featureset : public mapnik::Featureset
|
|
||||||
{
|
|
||||||
struct query_dispatch
|
|
||||||
{
|
|
||||||
query_dispatch( rasterlite_featureset & featureset)
|
|
||||||
: featureset_(featureset) {}
|
|
||||||
|
|
||||||
mapnik::feature_ptr operator() (mapnik::query const& q) const
|
|
||||||
{
|
|
||||||
return featureset_.get_feature(q);
|
|
||||||
}
|
|
||||||
|
|
||||||
mapnik::feature_ptr operator() (mapnik::coord2d const& p) const
|
|
||||||
{
|
|
||||||
return featureset_.get_feature_at_point(p);
|
|
||||||
}
|
|
||||||
|
|
||||||
rasterlite_featureset & featureset_;
|
|
||||||
};
|
|
||||||
|
|
||||||
public:
|
|
||||||
rasterlite_featureset(void* dataset,
|
|
||||||
rasterlite_query q);
|
|
||||||
virtual ~rasterlite_featureset();
|
|
||||||
mapnik::feature_ptr next();
|
|
||||||
|
|
||||||
private:
|
|
||||||
mapnik::feature_ptr get_feature(mapnik::query const& q);
|
|
||||||
mapnik::feature_ptr get_feature_at_point(mapnik::coord2d const& p);
|
|
||||||
void* dataset_;
|
|
||||||
rasterlite_query gquery_;
|
|
||||||
bool first_;
|
|
||||||
mapnik::context_ptr ctx_;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // RASTERLITE_FEATURESET_HPP
|
|
|
@ -1,31 +0,0 @@
|
||||||
/*****************************************************************************
|
|
||||||
*
|
|
||||||
* This file is part of Mapnik (c++ mapping toolkit)
|
|
||||||
*
|
|
||||||
* Copyright (C) 2015 Artem Pavlenko
|
|
||||||
*
|
|
||||||
* This library is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU Lesser General Public
|
|
||||||
* License as published by the Free Software Foundation; either
|
|
||||||
* version 2.1 of the License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This library is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
||||||
* Lesser General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Lesser General Public
|
|
||||||
* License along with this library; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
||||||
*
|
|
||||||
*****************************************************************************/
|
|
||||||
|
|
||||||
#ifndef RASTERLITE_INCLUDE_HPP
|
|
||||||
#define RASTERLITE_INCLUDE_HPP
|
|
||||||
|
|
||||||
extern "C" {
|
|
||||||
#include <sqlite3.h>
|
|
||||||
#include <rasterlite.h>
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif // RASTERLITE_INCLUDE_HPP
|
|
Loading…
Reference in a new issue