add support for relative paths for entities when using libxml2 and loading xml from string - thanks dodobas for the initial patch
This commit is contained in:
parent
c1ed612b2d
commit
d0b4db9ba3
12 changed files with 108 additions and 12 deletions
|
@ -263,7 +263,7 @@ bool has_pycairo()
|
|||
|
||||
|
||||
BOOST_PYTHON_FUNCTION_OVERLOADS(load_map_overloads, load_map, 2, 3);
|
||||
BOOST_PYTHON_FUNCTION_OVERLOADS(load_map_string_overloads, load_map_string, 2, 3);
|
||||
BOOST_PYTHON_FUNCTION_OVERLOADS(load_map_string_overloads, load_map_string, 2, 4);
|
||||
BOOST_PYTHON_FUNCTION_OVERLOADS(save_map_overloads, save_map, 2, 3);
|
||||
BOOST_PYTHON_FUNCTION_OVERLOADS(save_map_string_overloads, save_map_string, 1, 2);
|
||||
|
||||
|
|
|
@ -30,7 +30,7 @@
|
|||
namespace mapnik
|
||||
{
|
||||
void read_xml2( std::string const & filename, boost::property_tree::ptree & pt);
|
||||
void read_xml2_string( std::string const & str, boost::property_tree::ptree & pt);
|
||||
void read_xml2_string( std::string const & str, boost::property_tree::ptree & pt, std::string const & base_path="");
|
||||
}
|
||||
|
||||
#endif // LIBXML2_LOADER_INCLUDED
|
||||
|
|
|
@ -34,7 +34,7 @@
|
|||
namespace mapnik
|
||||
{
|
||||
MAPNIK_DECL void load_map(Map & map, std::string const& filename, bool strict = false);
|
||||
MAPNIK_DECL void load_map_string(Map & map, std::string const& str, bool strict = false);
|
||||
MAPNIK_DECL void load_map_string(Map & map, std::string const& str, bool strict = false, std::string const& base_url="");
|
||||
}
|
||||
|
||||
#endif // LOAD_MAP_HPP
|
||||
|
|
|
@ -37,6 +37,7 @@
|
|||
using boost::property_tree::ptree;
|
||||
using namespace std;
|
||||
|
||||
//#define DEFAULT_OPTIONS (XML_PARSE_NOENT | XML_PARSE_NOBLANKS | XML_PARSE_DTDLOAD | XML_PARSE_NOCDATA)
|
||||
#define DEFAULT_OPTIONS (XML_PARSE_NOERROR | XML_PARSE_NOENT | XML_PARSE_NOBLANKS | XML_PARSE_DTDLOAD | XML_PARSE_NOCDATA)
|
||||
|
||||
namespace mapnik
|
||||
|
@ -69,7 +70,7 @@ namespace mapnik
|
|||
void load( const std::string & filename, ptree & pt )
|
||||
{
|
||||
boost::filesystem::path path(filename);
|
||||
if ( ! boost::filesystem::exists( path ) ) {
|
||||
if ( !boost::filesystem::exists( path ) ) {
|
||||
throw config_error(string("Could not load map file '") +
|
||||
filename + "': File does not exist");
|
||||
}
|
||||
|
@ -114,9 +115,19 @@ namespace mapnik
|
|||
load(doc, pt);
|
||||
}
|
||||
|
||||
void load_string( const std::string & buffer, ptree & pt )
|
||||
void load_string( const std::string & buffer, ptree & pt, std::string const & base_url )
|
||||
{
|
||||
xmlDocPtr doc = xmlCtxtReadMemory(ctx_, buffer.data(), buffer.length(), url_, encoding_, options_);
|
||||
if (!base_url.empty())
|
||||
{
|
||||
boost::filesystem::path path(base_url);
|
||||
if ( ! boost::filesystem::exists( path ) ) {
|
||||
throw config_error(string("Could not locate base_url '") +
|
||||
base_url + "': file or directory does not exist");
|
||||
}
|
||||
}
|
||||
|
||||
xmlDocPtr doc = xmlCtxtReadMemory(ctx_, buffer.data(), buffer.length(), base_url.c_str(), encoding_, options_);
|
||||
|
||||
load(doc, pt);
|
||||
}
|
||||
|
||||
|
@ -203,10 +214,10 @@ namespace mapnik
|
|||
libxml2_loader loader;
|
||||
loader.load( filename, pt );
|
||||
}
|
||||
void read_xml2_string( std::string const & str, boost::property_tree::ptree & pt)
|
||||
void read_xml2_string( std::string const & str, boost::property_tree::ptree & pt, std::string const & base_url)
|
||||
{
|
||||
libxml2_loader loader;
|
||||
loader.load_string( str, pt );
|
||||
loader.load_string( str, pt, base_url );
|
||||
}
|
||||
|
||||
} // end of namespace mapnik
|
||||
|
|
|
@ -122,11 +122,11 @@ namespace mapnik
|
|||
parser.parse_map(map, pt);
|
||||
}
|
||||
|
||||
void load_map_string(Map & map, std::string const& str, bool strict)
|
||||
void load_map_string(Map & map, std::string const& str, bool strict, std::string const& base_url)
|
||||
{
|
||||
ptree pt;
|
||||
#ifdef HAVE_LIBXML2
|
||||
read_xml2_string(str, pt);
|
||||
read_xml2_string(str, pt, base_url);
|
||||
#else
|
||||
try
|
||||
{
|
||||
|
@ -139,7 +139,7 @@ namespace mapnik
|
|||
}
|
||||
#endif
|
||||
|
||||
map_parser parser( strict );
|
||||
map_parser parser( strict, base_url);
|
||||
parser.parse_map(map, pt);
|
||||
}
|
||||
|
||||
|
|
22
tests/data/good_maps/entities.xml
Normal file
22
tests/data/good_maps/entities.xml
Normal file
|
@ -0,0 +1,22 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!DOCTYPE Map [
|
||||
<!ENTITY % entities SYSTEM "../inc/entities.xml.inc">
|
||||
%entities;
|
||||
]>
|
||||
<Map bgcolor="#b5d0d0" srs="&srs900913;">
|
||||
&fontset-settings;
|
||||
<Style name="turning_circle">
|
||||
<Rule>
|
||||
&maxscale_zoom15;
|
||||
&minscale_zoom16;
|
||||
<PointSymbolizer file="&symbols;/dummy.png" type="png" width="15" height="15" />
|
||||
</Rule>
|
||||
<Rule>
|
||||
&maxscale_zoom17;
|
||||
<PointSymbolizer file="&symbols;/dummy.png" type="png" width="19" height="19" />
|
||||
</Rule>
|
||||
</Style>
|
||||
<Layer name="area-text" status="on" srs="&srs900913;">
|
||||
<StyleName>turning_circle</StyleName>
|
||||
</Layer>
|
||||
</Map>
|
7
tests/data/inc/entities.xml.inc
Normal file
7
tests/data/inc/entities.xml.inc
Normal file
|
@ -0,0 +1,7 @@
|
|||
<!ENTITY fontset-settings SYSTEM "fontset-settings.xml.inc">
|
||||
<!ENTITY srs900913 "+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +no_defs +over">
|
||||
<!ENTITY srsmercator "+proj=merc +datum=WGS84 +over">
|
||||
<!ENTITY srs4326 "+init=epsg:4326">
|
||||
<!ENTITY symbols "../images">
|
||||
<!ENTITY % scales SYSTEM "scales.xml.inc">
|
||||
%scales;
|
0
tests/data/inc/expected.xml
Normal file
0
tests/data/inc/expected.xml
Normal file
12
tests/data/inc/fontset-settings.xml.inc
Normal file
12
tests/data/inc/fontset-settings.xml.inc
Normal file
|
@ -0,0 +1,12 @@
|
|||
<FontSet name="book-fonts">
|
||||
<Font face_name="DejaVu Sans Book" />
|
||||
<!--Font face_name="unifont Medium" /-->
|
||||
</FontSet>
|
||||
<FontSet name="bold-fonts">
|
||||
<Font face_name="DejaVu Sans Bold" />
|
||||
<!--Font face_name="unifont Medium" /-->
|
||||
</FontSet>
|
||||
<FontSet name="oblique-fonts">
|
||||
<Font face_name="DejaVu Sans Oblique" />
|
||||
<!--Font face_name="unifont Medium" /-->
|
||||
</FontSet>
|
37
tests/data/inc/scales.xml.inc
Normal file
37
tests/data/inc/scales.xml.inc
Normal file
|
@ -0,0 +1,37 @@
|
|||
<!ENTITY maxscale_zoom0 "<MaxScaleDenominator>250000000000</MaxScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom1 "<MaxScaleDenominator>500000000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom1 "<MinScaleDenominator>200000000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom2 "<MaxScaleDenominator>200000000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom2 "<MinScaleDenominator>100000000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom3 "<MaxScaleDenominator>100000000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom3 "<MinScaleDenominator>50000000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom4 "<MaxScaleDenominator>50000000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom4 "<MinScaleDenominator>25000000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom5 "<MaxScaleDenominator>25000000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom5 "<MinScaleDenominator>12500000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom6 "<MaxScaleDenominator>12500000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom6 "<MinScaleDenominator>6500000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom7 "<MaxScaleDenominator>6500000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom7 "<MinScaleDenominator>3000000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom8 "<MaxScaleDenominator>3000000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom8 "<MinScaleDenominator>1500000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom9 "<MaxScaleDenominator>1500000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom9 "<MinScaleDenominator>750000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom10 "<MaxScaleDenominator>750000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom10 "<MinScaleDenominator>400000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom11 "<MaxScaleDenominator>400000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom11 "<MinScaleDenominator>200000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom12 "<MaxScaleDenominator>200000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom12 "<MinScaleDenominator>100000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom13 "<MaxScaleDenominator>100000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom13 "<MinScaleDenominator>50000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom14 "<MaxScaleDenominator>50000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom14 "<MinScaleDenominator>25000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom15 "<MaxScaleDenominator>25000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom15 "<MinScaleDenominator>12500</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom16 "<MaxScaleDenominator>12500</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom16 "<MinScaleDenominator>5000</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom17 "<MaxScaleDenominator>5000</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom17 "<MinScaleDenominator>2500</MinScaleDenominator>">
|
||||
<!ENTITY maxscale_zoom18 "<MaxScaleDenominator>2500</MaxScaleDenominator>">
|
||||
<!ENTITY minscale_zoom18 "<MinScaleDenominator>1000</MinScaleDenominator>">
|
|
@ -17,6 +17,12 @@ def assert_loads_successfully(file):
|
|||
|
||||
strict = True
|
||||
mapnik.load_map(m, file, strict)
|
||||
|
||||
# libxml2 is not smart about paths, and clips the last directory off
|
||||
# of a path if it does not end in a trailing slash
|
||||
base_path = os.path.dirname(file) + '/'
|
||||
mapnik.load_map_from_string(m,open(file,'rb').read(),strict,base_path)
|
||||
|
||||
|
||||
# We expect these files to raise a UserWarning
|
||||
# and fail if there isn't one (or a different type
|
||||
|
|
|
@ -262,7 +262,8 @@ def test_map_init_from_string():
|
|||
m = mapnik.Map(600, 300)
|
||||
|
||||
mapnik.load_map_from_string(m, map_string)
|
||||
mapnik.load_map_from_string(m, map_string, True)
|
||||
mapnik.load_map_from_string(m, map_string, False, "")
|
||||
mapnik.load_map_from_string(m, map_string, True, "")
|
||||
raise(Todo("Need to write more map property tests in 'object_test.py'..."))
|
||||
|
||||
# Map pickling
|
||||
|
|
Loading…
Reference in a new issue