From 82b91734d9192285ed82ec6152edcec81ffd14d4 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Mon, 23 Jan 2023 09:52:22 +0000 Subject: [PATCH 01/37] [WIP] refactor/enumerations https://github.com/mapnik/mapnik/pull/4372 --- src/mapnik_datasource.cpp | 7 +-- src/mapnik_enumeration.hpp | 8 ++- src/mapnik_gamma_method.cpp | 10 ++-- src/mapnik_raster_colorizer.cpp | 8 +-- src/mapnik_style.cpp | 4 +- src/mapnik_symbolizer.cpp | 86 ++++++++++++++++----------------- 6 files changed, 61 insertions(+), 62 deletions(-) diff --git a/src/mapnik_datasource.cpp b/src/mapnik_datasource.cpp index f180e7dd5..ec1c4c992 100644 --- a/src/mapnik_datasource.cpp +++ b/src/mapnik_datasource.cpp @@ -38,11 +38,11 @@ #include #include #include -#include +//#include using mapnik::datasource; -using mapnik::memory_datasource; +//using mapnik::memory_datasource; using mapnik::layer_descriptor; using mapnik::attribute_descriptor; using mapnik::parameters; @@ -197,7 +197,7 @@ void export_datasource() ; def("CreateDatasource",&create_datasource); - + /* class_, std::shared_ptr, boost::noncopyable>("MemoryDatasourceBase", init()) @@ -210,4 +210,5 @@ void export_datasource() ; implicitly_convertible,std::shared_ptr >(); + */ } diff --git a/src/mapnik_enumeration.hpp b/src/mapnik_enumeration.hpp index 6e13abe55..663a1489c 100644 --- a/src/mapnik_enumeration.hpp +++ b/src/mapnik_enumeration.hpp @@ -68,7 +68,7 @@ class enumeration_ : using namespace boost::python::converter; return base_type::base::to_python( registered::converters.m_class_object - , static_cast( v )); + , static_cast(native_type(v))); } }; @@ -76,11 +76,9 @@ class enumeration_ : void init() { boost::python::implicitly_convertible(); boost::python::to_python_converter(); - - for (unsigned i = 0; i < EnumWrapper::MAX; ++i) + for (auto const& kv : EnumWrapper::lookupMap()) { - // Register the strings already defined for this enum. - base_type::value( EnumWrapper::get_string( i ), native_type( i ) ); + base_type::value(kv.second.c_str(), kv.first); } } diff --git a/src/mapnik_gamma_method.cpp b/src/mapnik_gamma_method.cpp index d0ba6f725..178da6175 100644 --- a/src/mapnik_gamma_method.cpp +++ b/src/mapnik_gamma_method.cpp @@ -36,11 +36,11 @@ void export_gamma_method() using namespace boost::python; mapnik::enumeration_("gamma_method") - .value("POWER", mapnik::GAMMA_POWER) - .value("LINEAR",mapnik::GAMMA_LINEAR) - .value("NONE", mapnik::GAMMA_NONE) - .value("THRESHOLD", mapnik::GAMMA_THRESHOLD) - .value("MULTIPLY", mapnik::GAMMA_MULTIPLY) + .value("POWER", mapnik::gamma_method_enum::GAMMA_POWER) + .value("LINEAR",mapnik::gamma_method_enum::GAMMA_LINEAR) + .value("NONE", mapnik::gamma_method_enum::GAMMA_NONE) + .value("THRESHOLD", mapnik::gamma_method_enum::GAMMA_THRESHOLD) + .value("MULTIPLY", mapnik::gamma_method_enum::GAMMA_MULTIPLY) ; } diff --git a/src/mapnik_raster_colorizer.cpp b/src/mapnik_raster_colorizer.cpp index 6a8a709b3..e8b9abba1 100644 --- a/src/mapnik_raster_colorizer.cpp +++ b/src/mapnik_raster_colorizer.cpp @@ -40,10 +40,10 @@ using mapnik::colorizer_stop; using mapnik::colorizer_stops; using mapnik::colorizer_mode_enum; using mapnik::color; -using mapnik::COLORIZER_INHERIT; -using mapnik::COLORIZER_LINEAR; -using mapnik::COLORIZER_DISCRETE; -using mapnik::COLORIZER_EXACT; +using mapnik::colorizer_mode_enum::COLORIZER_INHERIT; +using mapnik::colorizer_mode_enum::COLORIZER_LINEAR; +using mapnik::colorizer_mode_enum::COLORIZER_DISCRETE; +using mapnik::colorizer_mode_enum::COLORIZER_EXACT; namespace { diff --git a/src/mapnik_style.cpp b/src/mapnik_style.cpp index 182943669..0353a472e 100644 --- a/src/mapnik_style.cpp +++ b/src/mapnik_style.cpp @@ -69,8 +69,8 @@ void export_style() using namespace boost::python; mapnik::enumeration_("filter_mode") - .value("ALL",mapnik::FILTER_ALL) - .value("FIRST",mapnik::FILTER_FIRST) + .value("ALL",mapnik::filter_mode_enum::FILTER_ALL) + .value("FIRST",mapnik::filter_mode_enum::FILTER_FIRST) ; class_("Rules",init<>("default ctor")) diff --git a/src/mapnik_symbolizer.cpp b/src/mapnik_symbolizer.cpp index ddbedf7e2..36f414b32 100644 --- a/src/mapnik_symbolizer.cpp +++ b/src/mapnik_symbolizer.cpp @@ -277,38 +277,38 @@ void export_text_symbolizer() { using namespace boost::python; mapnik::enumeration_("label_placement") - .value("LINE_PLACEMENT", mapnik::LINE_PLACEMENT) - .value("POINT_PLACEMENT", mapnik::POINT_PLACEMENT) - .value("VERTEX_PLACEMENT", mapnik::VERTEX_PLACEMENT) - .value("INTERIOR_PLACEMENT", mapnik::INTERIOR_PLACEMENT); + .value("LINE_PLACEMENT", mapnik::label_placement_enum::LINE_PLACEMENT) + .value("POINT_PLACEMENT", mapnik::label_placement_enum::POINT_PLACEMENT) + .value("VERTEX_PLACEMENT", mapnik::label_placement_enum::VERTEX_PLACEMENT) + .value("INTERIOR_PLACEMENT", mapnik::label_placement_enum::INTERIOR_PLACEMENT); mapnik::enumeration_("vertical_alignment") - .value("TOP", mapnik::V_TOP) - .value("MIDDLE", mapnik::V_MIDDLE) - .value("BOTTOM", mapnik::V_BOTTOM) - .value("AUTO", mapnik::V_AUTO); + .value("TOP", mapnik::vertical_alignment_enum::V_TOP) + .value("MIDDLE", mapnik::vertical_alignment_enum::V_MIDDLE) + .value("BOTTOM", mapnik::vertical_alignment_enum::V_BOTTOM) + .value("AUTO", mapnik::vertical_alignment_enum::V_AUTO); mapnik::enumeration_("horizontal_alignment") - .value("LEFT", mapnik::H_LEFT) - .value("MIDDLE", mapnik::H_MIDDLE) - .value("RIGHT", mapnik::H_RIGHT) - .value("AUTO", mapnik::H_AUTO); + .value("LEFT", mapnik::horizontal_alignment_enum::H_LEFT) + .value("MIDDLE", mapnik::horizontal_alignment_enum::H_MIDDLE) + .value("RIGHT", mapnik::horizontal_alignment_enum::H_RIGHT) + .value("AUTO", mapnik::horizontal_alignment_enum::H_AUTO); mapnik::enumeration_("justify_alignment") - .value("LEFT", mapnik::J_LEFT) - .value("MIDDLE", mapnik::J_MIDDLE) - .value("RIGHT", mapnik::J_RIGHT) - .value("AUTO", mapnik::J_AUTO); + .value("LEFT", mapnik::justify_alignment_enum::J_LEFT) + .value("MIDDLE", mapnik::justify_alignment_enum::J_MIDDLE) + .value("RIGHT", mapnik::justify_alignment_enum::J_RIGHT) + .value("AUTO", mapnik::justify_alignment_enum::J_AUTO); mapnik::enumeration_("text_transform") - .value("NONE", mapnik::NONE) - .value("UPPERCASE", mapnik::UPPERCASE) - .value("LOWERCASE", mapnik::LOWERCASE) - .value("CAPITALIZE", mapnik::CAPITALIZE); + .value("NONE", mapnik::text_transform_enum::NONE) + .value("UPPERCASE", mapnik::text_transform_enum::UPPERCASE) + .value("LOWERCASE", mapnik::text_transform_enum::LOWERCASE) + .value("CAPITALIZE", mapnik::text_transform_enum::CAPITALIZE); mapnik::enumeration_("halo_rasterizer") - .value("FULL", mapnik::HALO_RASTERIZER_FULL) - .value("FAST", mapnik::HALO_RASTERIZER_FAST); + .value("FULL", mapnik::halo_rasterizer_enum::HALO_RASTERIZER_FULL) + .value("FAST", mapnik::halo_rasterizer_enum::HALO_RASTERIZER_FAST); class_< text_symbolizer, bases >("TextSymbolizer", init<>("Default ctor")) @@ -343,8 +343,8 @@ void export_polygon_pattern_symbolizer() using namespace boost::python; mapnik::enumeration_("pattern_alignment") - .value("LOCAL",mapnik::LOCAL_ALIGNMENT) - .value("GLOBAL",mapnik::GLOBAL_ALIGNMENT) + .value("LOCAL",mapnik::pattern_alignment_enum::LOCAL_ALIGNMENT) + .value("GLOBAL",mapnik::pattern_alignment_enum::GLOBAL_ALIGNMENT) ; class_("PolygonPatternSymbolizer", @@ -367,8 +367,8 @@ void export_point_symbolizer() using namespace boost::python; mapnik::enumeration_("point_placement") - .value("CENTROID",mapnik::CENTROID_POINT_PLACEMENT) - .value("INTERIOR",mapnik::INTERIOR_POINT_PLACEMENT) + .value("CENTROID",mapnik::point_placement_enum::CENTROID_POINT_PLACEMENT) + .value("INTERIOR",mapnik::point_placement_enum::INTERIOR_POINT_PLACEMENT) ; class_ >("PointSymbolizer", @@ -382,15 +382,15 @@ void export_markers_symbolizer() using namespace boost::python; mapnik::enumeration_("marker_placement") - .value("POINT_PLACEMENT",mapnik::MARKER_POINT_PLACEMENT) - .value("INTERIOR_PLACEMENT",mapnik::MARKER_INTERIOR_PLACEMENT) - .value("LINE_PLACEMENT",mapnik::MARKER_LINE_PLACEMENT) + .value("POINT_PLACEMENT",mapnik::marker_placement_enum::MARKER_POINT_PLACEMENT) + .value("INTERIOR_PLACEMENT",mapnik::marker_placement_enum::MARKER_INTERIOR_PLACEMENT) + .value("LINE_PLACEMENT",mapnik::marker_placement_enum::MARKER_LINE_PLACEMENT) ; mapnik::enumeration_("marker_multi_policy") - .value("EACH",mapnik::MARKER_EACH_MULTI) - .value("WHOLE",mapnik::MARKER_WHOLE_MULTI) - .value("LARGEST",mapnik::MARKER_LARGEST_MULTI) + .value("EACH",mapnik::marker_multi_policy_enum::MARKER_EACH_MULTI) + .value("WHOLE",mapnik::marker_multi_policy_enum::MARKER_WHOLE_MULTI) + .value("LARGEST",mapnik::marker_multi_policy_enum::MARKER_LARGEST_MULTI) ; class_ >("MarkersSymbolizer", @@ -405,25 +405,25 @@ void export_line_symbolizer() using namespace boost::python; mapnik::enumeration_("line_rasterizer") - .value("FULL",mapnik::RASTERIZER_FULL) - .value("FAST",mapnik::RASTERIZER_FAST) + .value("FULL",mapnik::line_rasterizer_enum::RASTERIZER_FULL) + .value("FAST",mapnik::line_rasterizer_enum::RASTERIZER_FAST) ; mapnik::enumeration_("stroke_linecap", "The possible values for a line cap used when drawing\n" "with a stroke.\n") - .value("BUTT_CAP",mapnik::BUTT_CAP) - .value("SQUARE_CAP",mapnik::SQUARE_CAP) - .value("ROUND_CAP",mapnik::ROUND_CAP) + .value("BUTT_CAP",mapnik::line_cap_enum::BUTT_CAP) + .value("SQUARE_CAP",mapnik::line_cap_enum::SQUARE_CAP) + .value("ROUND_CAP",mapnik::line_cap_enum::ROUND_CAP) ; mapnik::enumeration_("stroke_linejoin", "The possible values for the line joining mode\n" "when drawing with a stroke.\n") - .value("MITER_JOIN",mapnik::MITER_JOIN) - .value("MITER_REVERT_JOIN",mapnik::MITER_REVERT_JOIN) - .value("ROUND_JOIN",mapnik::ROUND_JOIN) - .value("BEVEL_JOIN",mapnik::BEVEL_JOIN) + .value("MITER_JOIN",mapnik::line_join_enum::MITER_JOIN) + .value("MITER_REVERT_JOIN",mapnik::line_join_enum::MITER_REVERT_JOIN) + .value("ROUND_JOIN",mapnik::line_join_enum::ROUND_JOIN) + .value("BEVEL_JOIN",mapnik::line_join_enum::BEVEL_JOIN) ; @@ -448,8 +448,8 @@ void export_debug_symbolizer() using namespace boost::python; mapnik::enumeration_("debug_symbolizer_mode") - .value("COLLISION",mapnik::DEBUG_SYM_MODE_COLLISION) - .value("VERTEX",mapnik::DEBUG_SYM_MODE_VERTEX) + .value("COLLISION",mapnik::debug_symbolizer_mode_enum::DEBUG_SYM_MODE_COLLISION) + .value("VERTEX",mapnik::debug_symbolizer_mode_enum::DEBUG_SYM_MODE_VERTEX) ; class_ >("DebugSymbolizer", From c368066e5bd10b0a58d3f5494e7bde6698948ddd Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Tue, 24 Jan 2023 14:18:41 +0000 Subject: [PATCH 02/37] [WIP] restore `memory_datasource` https://github.com/mapnik/mapnik/pull/4377 --- src/mapnik_datasource.cpp | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/src/mapnik_datasource.cpp b/src/mapnik_datasource.cpp index ec1c4c992..f180e7dd5 100644 --- a/src/mapnik_datasource.cpp +++ b/src/mapnik_datasource.cpp @@ -38,11 +38,11 @@ #include #include #include -//#include +#include using mapnik::datasource; -//using mapnik::memory_datasource; +using mapnik::memory_datasource; using mapnik::layer_descriptor; using mapnik::attribute_descriptor; using mapnik::parameters; @@ -197,7 +197,7 @@ void export_datasource() ; def("CreateDatasource",&create_datasource); - /* + class_, std::shared_ptr, boost::noncopyable>("MemoryDatasourceBase", init()) @@ -210,5 +210,4 @@ void export_datasource() ; implicitly_convertible,std::shared_ptr >(); - */ } From 372dba1356f02eb8773f3bd3d50c3ecd67a8f288 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Tue, 24 Jan 2023 14:46:16 +0000 Subject: [PATCH 03/37] [WIP] remove redundant declarations --- src/mapnik_raster_colorizer.cpp | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) diff --git a/src/mapnik_raster_colorizer.cpp b/src/mapnik_raster_colorizer.cpp index e8b9abba1..1dd524313 100644 --- a/src/mapnik_raster_colorizer.cpp +++ b/src/mapnik_raster_colorizer.cpp @@ -40,11 +40,6 @@ using mapnik::colorizer_stop; using mapnik::colorizer_stops; using mapnik::colorizer_mode_enum; using mapnik::color; -using mapnik::colorizer_mode_enum::COLORIZER_INHERIT; -using mapnik::colorizer_mode_enum::COLORIZER_LINEAR; -using mapnik::colorizer_mode_enum::COLORIZER_DISCRETE; -using mapnik::colorizer_mode_enum::COLORIZER_EXACT; - namespace { void add_stop(raster_colorizer_ptr & rc, colorizer_stop & stop) @@ -196,10 +191,10 @@ void export_raster_colorizer() ; enum_("ColorizerMode") - .value("COLORIZER_INHERIT", COLORIZER_INHERIT) - .value("COLORIZER_LINEAR", COLORIZER_LINEAR) - .value("COLORIZER_DISCRETE", COLORIZER_DISCRETE) - .value("COLORIZER_EXACT", COLORIZER_EXACT) + .value("COLORIZER_INHERIT", colorizer_mode_enum::COLORIZER_INHERIT) + .value("COLORIZER_LINEAR", colorizer_mode_enum::COLORIZER_LINEAR) + .value("COLORIZER_DISCRETE", colorizer_mode_enum::COLORIZER_DISCRETE) + .value("COLORIZER_EXACT", colorizer_mode_enum::COLORIZER_EXACT) .export_values() ; From 0d3ed79d396051b1f97bf232b6d27437dfd16af1 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 26 Jan 2023 21:25:57 +0000 Subject: [PATCH 04/37] convert some unit tests to use pytest [WIP] --- .../agg_rasterizer_integer_overflow_test.py | 17 +- test/python_tests/box2d_test.py | 295 ++++++++---------- test/python_tests/buffer_clear_test.py | 29 +- test/python_tests/cairo_test.py | 59 ++-- test/python_tests/color_test.py | 161 +++++----- test/python_tests/compare_test.py | 94 +++--- .../images/pycairo/cairo-cairo-expected.pdf | Bin 4340 -> 8148 bytes test/python_tests/topojson_plugin_test.py | 146 ++++----- test/python_tests/utilities.py | 15 - 9 files changed, 333 insertions(+), 483 deletions(-) diff --git a/test/python_tests/agg_rasterizer_integer_overflow_test.py b/test/python_tests/agg_rasterizer_integer_overflow_test.py index 1f984fb61..2a8c08571 100644 --- a/test/python_tests/agg_rasterizer_integer_overflow_test.py +++ b/test/python_tests/agg_rasterizer_integer_overflow_test.py @@ -1,14 +1,6 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - import json - -from nose.tools import eq_ - import mapnik -from .utilities import run_all - # geojson box of the world geojson = {"type": "Feature", "properties": {}, @@ -24,7 +16,6 @@ [-17963313.143242701888084, -6300857.11560364998877]]]}} - def test_that_coordinates_do_not_overflow_and_polygon_is_rendered_memory(): expected_color = mapnik.Color('white') projection = 'epsg:4326' @@ -52,8 +43,7 @@ def test_that_coordinates_do_not_overflow_and_polygon_is_rendered_memory(): # m.zoom_to_box(mapnik.Box2d(-13658379.710221574,6195679.764683247,-13655933.72531645,6198125.749588372)) im = mapnik.Image(256, 256) mapnik.render(m, im) - eq_(im.get_pixel(128, 128), expected_color.packed()) - + assert im.get_pixel(128, 128) == expected_color.packed() def test_that_coordinates_do_not_overflow_and_polygon_is_rendered_csv(): expected_color = mapnik.Color('white') @@ -84,7 +74,4 @@ def test_that_coordinates_do_not_overflow_and_polygon_is_rendered_csv(): # m.zoom_to_box(mapnik.Box2d(-13658379.710221574,6195679.764683247,-13655933.72531645,6198125.749588372)) im = mapnik.Image(256, 256) mapnik.render(m, im) - eq_(im.get_pixel(128, 128), expected_color.packed()) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im.get_pixel(128, 128) == expected_color.packed() diff --git a/test/python_tests/box2d_test.py b/test/python_tests/box2d_test.py index 7fe0a9f59..e3a477003 100644 --- a/test/python_tests/box2d_test.py +++ b/test/python_tests/box2d_test.py @@ -1,184 +1,155 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -from nose.tools import assert_almost_equal, assert_false, assert_true, eq_ - import mapnik - -from .utilities import run_all - +import pytest def test_coord_init(): c = mapnik.Coord(100, 100) - - eq_(c.x, 100) - eq_(c.y, 100) - + assert c.x == 100 + assert c.y == 100 def test_coord_multiplication(): - c = mapnik.Coord(100, 100) - c *= 2 - - eq_(c.x, 200) - eq_(c.y, 200) - + c = mapnik.Coord(100, 100) + c *= 2 + assert c.x == 200 + assert c.y == 200 def test_envelope_init(): - e = mapnik.Box2d(100, 100, 200, 200) - - assert_true(e.contains(100, 100)) - assert_true(e.contains(100, 200)) - assert_true(e.contains(200, 200)) - assert_true(e.contains(200, 100)) - - assert_true(e.contains(e.center())) - - assert_false(e.contains(99.9, 99.9)) - assert_false(e.contains(99.9, 200.1)) - assert_false(e.contains(200.1, 200.1)) - assert_false(e.contains(200.1, 99.9)) - - eq_(e.width(), 100) - eq_(e.height(), 100) - - eq_(e.minx, 100) - eq_(e.miny, 100) - - eq_(e.maxx, 200) - eq_(e.maxy, 200) - - eq_(e[0], 100) - eq_(e[1], 100) - eq_(e[2], 200) - eq_(e[3], 200) - eq_(e[0], e[-4]) - eq_(e[1], e[-3]) - eq_(e[2], e[-2]) - eq_(e[3], e[-1]) - - c = e.center() - - eq_(c.x, 150) - eq_(c.y, 150) + e = mapnik.Box2d(100, 100, 200, 200) + assert e.contains(100, 100) + assert e.contains(100, 200) + assert e.contains(200, 200) + assert e.contains(200, 100) + assert e.contains(e.center()) + assert not e.contains(99.9, 99.9) + assert not e.contains(99.9, 200.1) + assert not e.contains(200.1, 200.1) + assert not e.contains(200.1, 99.9) + assert e.width() == 100 + assert e.height() == 100 + assert e.minx == 100 + assert e.miny == 100 + assert e.maxx == 200 + assert e.maxy == 200 + assert e[0] == 100 + assert e[1] == 100 + assert e[2] == 200 + assert e[3] == 200 + assert e[0] == e[-4] + assert e[1] == e[-3] + assert e[2] == e[-2] + assert e[3] == e[-1] + c = e.center() + assert c.x == 150 + assert c.y == 150 def test_envelope_static_init(): e = mapnik.Box2d.from_string('100 100 200 200') e2 = mapnik.Box2d.from_string('100,100,200,200') e3 = mapnik.Box2d.from_string('100 , 100 , 200 , 200') - eq_(e, e2) - eq_(e, e3) - - assert_true(e.contains(100, 100)) - assert_true(e.contains(100, 200)) - assert_true(e.contains(200, 200)) - assert_true(e.contains(200, 100)) - - assert_true(e.contains(e.center())) - - assert_false(e.contains(99.9, 99.9)) - assert_false(e.contains(99.9, 200.1)) - assert_false(e.contains(200.1, 200.1)) - assert_false(e.contains(200.1, 99.9)) - - eq_(e.width(), 100) - eq_(e.height(), 100) - eq_(e.minx, 100) - eq_(e.miny, 100) - - eq_(e.maxx, 200) - eq_(e.maxy, 200) - - eq_(e[0], 100) - eq_(e[1], 100) - eq_(e[2], 200) - eq_(e[3], 200) - eq_(e[0], e[-4]) - eq_(e[1], e[-3]) - eq_(e[2], e[-2]) - eq_(e[3], e[-1]) + assert e == e2 + assert e == e3 + assert e.contains(100, 100) + assert e.contains(100, 200) + assert e.contains(200, 200) + assert e.contains(200, 100) + + assert e.contains(e.center()) + assert not e.contains(99.9, 99.9) + assert not e.contains(99.9, 200.1) + assert not e.contains(200.1, 200.1) + assert not e.contains(200.1, 99.9) + + assert e.width() == 100 + assert e.height() == 100 + assert e.minx == 100 + assert e.miny == 100 + assert e.maxx == 200 + assert e.maxy == 200 + + assert e[0] == 100 + assert e[1] == 100 + assert e[2] == 200 + assert e[3] == 200 + assert e[0] == e[-4] + assert e[1] == e[-3] + assert e[2] == e[-2] + assert e[3] == e[-1] c = e.center() - - eq_(c.x, 150) - eq_(c.y, 150) - + assert c.x == 150 + assert c.y == 150 def test_envelope_multiplication(): - # no width then no impact of multiplication - a = mapnik.Box2d(100, 100, 100, 100) - a *= 5 - eq_(a.minx, 100) - eq_(a.miny, 100) - eq_(a.maxx, 100) - eq_(a.maxy, 100) - - a = mapnik.Box2d(100.0, 100.0, 100.0, 100.0) - a *= 5 - eq_(a.minx, 100) - eq_(a.miny, 100) - eq_(a.maxx, 100) - eq_(a.maxy, 100) - - a = mapnik.Box2d(100.0, 100.0, 100.001, 100.001) - a *= 5 - assert_almost_equal(a.minx, 99.9979, places=3) - assert_almost_equal(a.miny, 99.9979, places=3) - assert_almost_equal(a.maxx, 100.0030, places=3) - assert_almost_equal(a.maxy, 100.0030, places=3) - - e = mapnik.Box2d(100, 100, 200, 200) - e *= 2 - eq_(e.minx, 50) - eq_(e.miny, 50) - eq_(e.maxx, 250) - eq_(e.maxy, 250) - - assert_true(e.contains(50, 50)) - assert_true(e.contains(50, 250)) - assert_true(e.contains(250, 250)) - assert_true(e.contains(250, 50)) - - assert_false(e.contains(49.9, 49.9)) - assert_false(e.contains(49.9, 250.1)) - assert_false(e.contains(250.1, 250.1)) - assert_false(e.contains(250.1, 49.9)) - - assert_true(e.contains(e.center())) - - eq_(e.width(), 200) - eq_(e.height(), 200) - - eq_(e.minx, 50) - eq_(e.miny, 50) - - eq_(e.maxx, 250) - eq_(e.maxy, 250) - - c = e.center() - - eq_(c.x, 150) - eq_(c.y, 150) + # no width then no impact of multiplication + a = mapnik.Box2d(100, 100, 100, 100) + a *= 5 + assert a.minx == 100 + assert a.miny == 100 + assert a.maxx == 100 + assert a.maxy == 100 + + a = mapnik.Box2d(100.0, 100.0, 100.0, 100.0) + a *= 5 + assert a.minx == 100 + assert a.miny == 100 + assert a.maxx == 100 + assert a.maxy == 100 + + a = mapnik.Box2d(100.0, 100.0, 100.001, 100.001) + a *= 5 + assert a.minx == pytest.approx(99.9979, 1e-3) + assert a.miny == pytest.approx(99.9979, 1e-3) + assert a.maxx == pytest.approx(100.0030,1e-3) + assert a.maxy == pytest.approx(100.0030,1e-3) + + e = mapnik.Box2d(100, 100, 200, 200) + e *= 2 + assert e.minx == 50 + assert e.miny == 50 + assert e.maxx == 250 + assert e.maxy == 250 + + assert e.contains(50, 50) + assert e.contains(50, 250) + assert e.contains(250, 250) + assert e.contains(250, 50) + + assert not e.contains(49.9, 49.9) + assert not e.contains(49.9, 250.1) + assert not e.contains(250.1, 250.1) + assert not e.contains(250.1, 49.9) + + c = e.center() + assert c.x == 150 + assert c.y == 150 + + assert e.contains(c) + + assert e.width() == 200 + assert e.height()== 200 + + assert e.minx == 50 + assert e.miny == 50 + + assert e.maxx == 250 + assert e.maxy == 250 def test_envelope_clipping(): - e1 = mapnik.Box2d(-180, -90, 180, 90) - e2 = mapnik.Box2d(-120, 40, -110, 48) - e1.clip(e2) - eq_(e1, e2) - - # madagascar in merc - e1 = mapnik.Box2d(4772116.5490, -2744395.0631, 5765186.4203, -1609458.0673) - e2 = mapnik.Box2d(5124338.3753, -2240522.1727, 5207501.8621, -2130452.8520) - e1.clip(e2) - eq_(e1, e2) - - # nz in lon/lat - e1 = mapnik.Box2d(163.8062, -47.1897, 179.3628, -33.9069) - e2 = mapnik.Box2d(173.7378, -39.6395, 174.4849, -38.9252) - e1.clip(e2) - eq_(e1, e2) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + e1 = mapnik.Box2d(-180, -90, 180, 90) + e2 = mapnik.Box2d(-120, 40, -110, 48) + e1.clip(e2) + assert e1 == e2 + + # madagascar in merc + e1 = mapnik.Box2d(4772116.5490, -2744395.0631, 5765186.4203, -1609458.0673) + e2 = mapnik.Box2d(5124338.3753, -2240522.1727, 5207501.8621, -2130452.8520) + e1.clip(e2) + assert e1 == e2 + +# # nz in lon/lat + e1 = mapnik.Box2d(163.8062, -47.1897, 179.3628, -33.9069) + e2 = mapnik.Box2d(173.7378, -39.6395, 174.4849, -38.9252) + e1.clip(e2) + assert e1 == e2 diff --git a/test/python_tests/buffer_clear_test.py b/test/python_tests/buffer_clear_test.py index b94e9e4c6..74b0ee13a 100644 --- a/test/python_tests/buffer_clear_test.py +++ b/test/python_tests/buffer_clear_test.py @@ -1,30 +1,17 @@ import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_clearing_image_data(): im = mapnik.Image(256, 256) # make sure it equals itself bytes = im.tostring() - eq_(im.tostring(), bytes) + assert im.tostring() == bytes # set background, then clear im.fill(mapnik.Color('green')) - eq_(im.tostring() != bytes, True) + assert not im.tostring() == bytes # clear image, should now equal original im.clear() - eq_(im.tostring(), bytes) - + assert im.tostring() == bytes def make_map(): ds = mapnik.MemoryDatasource() @@ -56,14 +43,10 @@ def test_clearing_grid_data(): g = mapnik.Grid(256, 256) utf = g.encode() # make sure it equals itself - eq_(g.encode(), utf) + assert g.encode() == utf m = make_map() mapnik.render_layer(m, g, layer=0, fields=['__id__', 'Name']) - eq_(g.encode() != utf, True) + assert g.encode() != utf # clear grid, should now match original g.clear() - eq_(g.encode(), utf) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert g.encode() == utf diff --git a/test/python_tests/cairo_test.py b/test/python_tests/cairo_test.py index c6c25a379..a296a91a2 100644 --- a/test/python_tests/cairo_test.py +++ b/test/python_tests/cairo_test.py @@ -1,23 +1,7 @@ -#!/usr/bin/env python - -from __future__ import print_function - import os import shutil - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def make_tmp_map(): m = mapnik.Map(512, 512) m.background_color = mapnik.Color('steelblue') @@ -41,13 +25,12 @@ def make_tmp_map(): m.layers.append(lyr) return m - def draw_title(m, ctx, text, size=10, color=mapnik.Color('black')): """ Draw a Map Title near the top of a page.""" middle = m.width / 2.0 ctx.set_source_rgba(*cairo_color(color)) ctx.select_font_face( - "DejaVu Sans Book", + "Helvetica", cairo.FONT_SLANT_NORMAL, cairo.FONT_WEIGHT_NORMAL) ctx.set_font_size(size) @@ -97,7 +80,7 @@ def test_passing_pycairo_context_svg(): m.zoom_to_box(mapnik.Box2d(-180, -90, 180, 90)) test_cairo_file = '/tmp/mapnik-cairo-context-test.svg' surface = cairo.SVGSurface(test_cairo_file, m.width, m.height) - expected_cairo_file = './images/pycairo/cairo-cairo-expected.svg' + expected_cairo_file = './test/python_tests/images/pycairo/cairo-cairo-expected.svg' context = cairo.Context(surface) mapnik.render(m, context) draw_title(m, context, "Hello Map", size=20) @@ -111,7 +94,7 @@ def test_passing_pycairo_context_svg(): os.stat(test_cairo_file).st_size) msg = 'diff in size (%s) between actual (%s) and expected(%s)' % ( diff, test_cairo_file, 'tests/python_tests/' + expected_cairo_file) - eq_(diff < 1500, True, msg) + assert diff < 1500, msg os.remove(test_cairo_file) def test_passing_pycairo_context_pdf(): @@ -119,7 +102,7 @@ def test_passing_pycairo_context_pdf(): m.zoom_to_box(mapnik.Box2d(-180, -90, 180, 90)) test_cairo_file = '/tmp/mapnik-cairo-context-test.pdf' surface = cairo.PDFSurface(test_cairo_file, m.width, m.height) - expected_cairo_file = './images/pycairo/cairo-cairo-expected.pdf' + expected_cairo_file = './test/python_tests/images/pycairo/cairo-cairo-expected.pdf' context = cairo.Context(surface) mapnik.render(m, context) draw_title(m, context, "Hello Map", size=20) @@ -133,7 +116,7 @@ def test_passing_pycairo_context_pdf(): os.stat(test_cairo_file).st_size) msg = 'diff in size (%s) between actual (%s) and expected(%s)' % ( diff, test_cairo_file, 'tests/python_tests/' + expected_cairo_file) - eq_(diff < 1500, True, msg) + assert diff < 1500, msg os.remove(test_cairo_file) def test_passing_pycairo_context_png(): @@ -141,8 +124,8 @@ def test_passing_pycairo_context_png(): m.zoom_to_box(mapnik.Box2d(-180, -90, 180, 90)) test_cairo_file = '/tmp/mapnik-cairo-context-test.png' surface = cairo.ImageSurface(cairo.FORMAT_ARGB32, m.width, m.height) - expected_cairo_file = './images/pycairo/cairo-cairo-expected.png' - expected_cairo_file2 = './images/pycairo/cairo-cairo-expected-reduced.png' + expected_cairo_file = './test/python_tests/images/pycairo/cairo-cairo-expected.png' + expected_cairo_file2 = './test/python_tests/images/pycairo/cairo-cairo-expected-reduced.png' context = cairo.Context(surface) mapnik.render(m, context) draw_title(m, context, "Hello Map", size=20) @@ -160,7 +143,7 @@ def test_passing_pycairo_context_png(): os.stat(test_cairo_file).st_size) msg = 'diff in size (%s) between actual (%s) and expected(%s)' % ( diff, test_cairo_file, 'tests/python_tests/' + expected_cairo_file) - eq_(diff < 500, True, msg) + assert diff < 500, msg os.remove(test_cairo_file) if not os.path.exists( expected_cairo_file2) or os.environ.get('UPDATE'): @@ -173,17 +156,17 @@ def test_passing_pycairo_context_png(): os.stat(reduced_color_image).st_size) msg = 'diff in size (%s) between actual (%s) and expected(%s)' % ( diff, reduced_color_image, 'tests/python_tests/' + expected_cairo_file2) - eq_(diff < 500, True, msg) + assert diff < 500, msg os.remove(reduced_color_image) if 'sqlite' in mapnik.DatasourceCache.plugin_names(): def _pycairo_surface(type, sym): test_cairo_file = '/tmp/mapnik-cairo-surface-test.%s.%s' % ( sym, type) - expected_cairo_file = './images/pycairo/cairo-surface-expected.%s.%s' % ( + expected_cairo_file = './test/python_tests/images/pycairo/cairo-surface-expected.%s.%s' % ( sym, type) m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/%s_symbolizer.xml' % sym) + mapnik.load_map(m, './test/data/good_maps/%s_symbolizer.xml' % sym) m.zoom_all() if hasattr(cairo, '%sSurface' % type.upper()): surface = getattr( @@ -207,9 +190,9 @@ def _pycairo_surface(type, sym): msg = 'diff in size (%s) between actual (%s) and expected(%s)' % ( diff, test_cairo_file, 'tests/python_tests/' + expected_cairo_file) if os.uname()[0] == 'Darwin': - eq_(diff < 2100, True, msg) + assert diff < 2100, msg else: - eq_(diff < 23000, True, msg) + assert diff < 23000, msg os.remove(test_cairo_file) return True else: @@ -219,23 +202,19 @@ def _pycairo_surface(type, sym): return True def test_pycairo_svg_surface1(): - eq_(_pycairo_surface('svg', 'point'), True) + assert _pycairo_surface('svg', 'point') def test_pycairo_svg_surface2(): - eq_(_pycairo_surface('svg', 'building'), True) + assert _pycairo_surface('svg', 'building') def test_pycairo_svg_surface3(): - eq_(_pycairo_surface('svg', 'polygon'), True) + assert _pycairo_surface('svg', 'polygon') def test_pycairo_pdf_surface1(): - eq_(_pycairo_surface('pdf', 'point'), True) + assert _pycairo_surface('pdf', 'point') def test_pycairo_pdf_surface2(): - eq_(_pycairo_surface('pdf', 'building'), True) + assert _pycairo_surface('pdf', 'building') def test_pycairo_pdf_surface3(): - eq_(_pycairo_surface('pdf', 'polygon'), True) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert _pycairo_surface('pdf', 'polygon') diff --git a/test/python_tests/color_test.py b/test/python_tests/color_test.py index 428843145..e8fc90fc6 100644 --- a/test/python_tests/color_test.py +++ b/test/python_tests/color_test.py @@ -1,121 +1,102 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_color_init(): c = mapnik.Color(12, 128, 255) - eq_(c.r, 12) - eq_(c.g, 128) - eq_(c.b, 255) - eq_(c.a, 255) - eq_(False, c.get_premultiplied()) + assert c.r == 12 + assert c.g == 128 + assert c.b == 255 + assert c.a == 255 + assert not c.get_premultiplied() c = mapnik.Color(16, 32, 64, 128) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(False, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert not c.get_premultiplied() c = mapnik.Color(16, 32, 64, 128, True) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(True, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert c.get_premultiplied() c = mapnik.Color('rgba(16,32,64,0.5)') - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(False, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert not c.get_premultiplied() c = mapnik.Color('rgba(16,32,64,0.5)', True) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(True, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert c.get_premultiplied() hex_str = '#10204080' c = mapnik.Color(hex_str) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(hex_str, c.to_hex_string()) - eq_(False, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert hex_str == c.to_hex_string() + assert not c.get_premultiplied() c = mapnik.Color(hex_str, True) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(hex_str, c.to_hex_string()) - eq_(True, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert hex_str == c.to_hex_string() + assert c.get_premultiplied() rgba_int = 2151686160 c = mapnik.Color(rgba_int) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(rgba_int, c.packed()) - eq_(False, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert rgba_int == c.packed() + assert not c.get_premultiplied() c = mapnik.Color(rgba_int, True) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) - eq_(rgba_int, c.packed()) - eq_(True, c.get_premultiplied()) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 + assert rgba_int == c.packed() + assert c.get_premultiplied() def test_color_properties(): c = mapnik.Color(16, 32, 64, 128) - eq_(c.r, 16) - eq_(c.g, 32) - eq_(c.b, 64) - eq_(c.a, 128) + assert c.r == 16 + assert c.g == 32 + assert c.b == 64 + assert c.a == 128 c.r = 17 - eq_(c.r, 17) + assert c.r == 17 c.g = 33 - eq_(c.g, 33) + assert c.g == 33 c.b = 65 - eq_(c.b, 65) + assert c.b == 65 c.a = 128 - eq_(c.a, 128) + assert c.a == 128 def test_color_premultiply(): c = mapnik.Color(16, 33, 255, 128) - eq_(c.premultiply(), True) - eq_(c.r, 8) - eq_(c.g, 17) - eq_(c.b, 128) - eq_(c.a, 128) + assert c.premultiply() + assert c.r == 8 + assert c.g == 17 + assert c.b == 128 + assert c.a == 128 # Repeating it again should do nothing - eq_(c.premultiply(), False) - eq_(c.r, 8) - eq_(c.g, 17) - eq_(c.b, 128) - eq_(c.a, 128) + assert not c.premultiply() + assert c.r == 8 + assert c.g == 17 + assert c.b == 128 + assert c.a == 128 c.demultiply() c.demultiply() # This will not return the same values as before but we expect that - eq_(c.r, 15) - eq_(c.g, 33) - eq_(c.b, 255) - eq_(c.a, 128) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert c.r == 15 + assert c.g == 33 + assert c.b == 255 + assert c.a == 128 diff --git a/test/python_tests/compare_test.py b/test/python_tests/compare_test.py index bb8397a2b..b66775262 100644 --- a/test/python_tests/compare_test.py +++ b/test/python_tests/compare_test.py @@ -1,48 +1,32 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_another_compare(): im = mapnik.Image(5, 5) im2 = mapnik.Image(5, 5) im2.fill(mapnik.Color('rgba(255,255,255,0)')) - eq_(im.compare(im2, 16), im.width() * im.height()) - + assert im.compare(im2, 16) == im.width() * im.height() def test_compare_rgba8(): im = mapnik.Image(5, 5, mapnik.ImageType.rgba8) im.fill(mapnik.Color(0, 0, 0, 0)) - eq_(im.compare(im), 0) + assert im.compare(im) == 0 im2 = mapnik.Image(5, 5, mapnik.ImageType.rgba8) im2.fill(mapnik.Color(0, 0, 0, 0)) - eq_(im.compare(im2), 0) - eq_(im2.compare(im), 0) + assert im.compare(im2) == 0 + assert im2.compare(im) == 0 im2.fill(mapnik.Color(0, 0, 0, 12)) - eq_(im.compare(im2), 25) - eq_(im.compare(im2, 0, False), 0) + assert im.compare(im2) == 25 + assert im.compare(im2, 0, False) == 0 im3 = mapnik.Image(5, 5, mapnik.ImageType.rgba8) im3.set_pixel(0, 0, mapnik.Color(0, 0, 0, 0)) im3.set_pixel(0, 1, mapnik.Color(1, 1, 1, 1)) im3.set_pixel(1, 0, mapnik.Color(2, 2, 2, 2)) im3.set_pixel(1, 1, mapnik.Color(3, 3, 3, 3)) - eq_(im.compare(im3), 3) - eq_(im.compare(im3, 1), 2) - eq_(im.compare(im3, 2), 1) - eq_(im.compare(im3, 3), 0) + assert im.compare(im3) == 3 + assert im.compare(im3, 1) == 2 + assert im.compare(im3, 2) == 1 + assert im.compare(im3, 3) == 0 def test_compare_2_image(): @@ -50,75 +34,71 @@ def test_compare_2_image(): im.set_pixel(0, 0, mapnik.Color(254, 254, 254, 254)) im.set_pixel(4, 4, mapnik.Color('white')) im2 = mapnik.Image(5, 5) - eq_(im2.compare(im, 16), 2) + assert im2.compare(im, 16) == 2 def test_compare_dimensions(): im = mapnik.Image(2, 2) im2 = mapnik.Image(3, 3) - eq_(im.compare(im2), 4) - eq_(im2.compare(im), 9) + assert im.compare(im2) == 4 + assert im2.compare(im) == 9 def test_compare_gray8(): im = mapnik.Image(2, 2, mapnik.ImageType.gray8) im.fill(0) - eq_(im.compare(im), 0) + assert im.compare(im) == 0 im2 = mapnik.Image(2, 2, mapnik.ImageType.gray8) im2.fill(0) - eq_(im.compare(im2), 0) - eq_(im2.compare(im), 0) - eq_(im.compare(im2, 0, False), 0) + assert im.compare(im2) == 0 + assert im2.compare(im) == 0 + assert im.compare(im2, 0, False) == 0 im3 = mapnik.Image(2, 2, mapnik.ImageType.gray8) im3.set_pixel(0, 0, 0) im3.set_pixel(0, 1, 1) im3.set_pixel(1, 0, 2) im3.set_pixel(1, 1, 3) - eq_(im.compare(im3), 3) - eq_(im.compare(im3, 1), 2) - eq_(im.compare(im3, 2), 1) - eq_(im.compare(im3, 3), 0) + assert im.compare(im3) == 3 + assert im.compare(im3, 1) == 2 + assert im.compare(im3, 2) == 1 + assert im.compare(im3, 3) == 0 def test_compare_gray16(): im = mapnik.Image(2, 2, mapnik.ImageType.gray16) im.fill(0) - eq_(im.compare(im), 0) + assert im.compare(im) == 0 im2 = mapnik.Image(2, 2, mapnik.ImageType.gray16) im2.fill(0) - eq_(im.compare(im2), 0) - eq_(im2.compare(im), 0) - eq_(im.compare(im2, 0, False), 0) + assert im.compare(im2) == 0 + assert im2.compare(im) == 0 + assert im.compare(im2, 0, False) == 0 im3 = mapnik.Image(2, 2, mapnik.ImageType.gray16) im3.set_pixel(0, 0, 0) im3.set_pixel(0, 1, 1) im3.set_pixel(1, 0, 2) im3.set_pixel(1, 1, 3) - eq_(im.compare(im3), 3) - eq_(im.compare(im3, 1), 2) - eq_(im.compare(im3, 2), 1) - eq_(im.compare(im3, 3), 0) + assert im.compare(im3) == 3 + assert im.compare(im3, 1) == 2 + assert im.compare(im3, 2) == 1 + assert im.compare(im3, 3) == 0 def test_compare_gray32f(): im = mapnik.Image(2, 2, mapnik.ImageType.gray32f) im.fill(0.5) - eq_(im.compare(im), 0) + assert im.compare(im) == 0 im2 = mapnik.Image(2, 2, mapnik.ImageType.gray32f) im2.fill(0.5) - eq_(im.compare(im2), 0) - eq_(im2.compare(im), 0) - eq_(im.compare(im2, 0, False), 0) + assert im.compare(im2) == 0 + assert im2.compare(im) == 0 + assert im.compare(im2, 0, False) == 0 im3 = mapnik.Image(2, 2, mapnik.ImageType.gray32f) im3.set_pixel(0, 0, 0.5) im3.set_pixel(0, 1, 1.5) im3.set_pixel(1, 0, 2.5) im3.set_pixel(1, 1, 3.5) - eq_(im.compare(im3), 3) - eq_(im.compare(im3, 1.0), 2) - eq_(im.compare(im3, 2.0), 1) - eq_(im.compare(im3, 3.0), 0) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im.compare(im3) == 3 + assert im.compare(im3, 1.0) == 2 + assert im.compare(im3, 2.0) == 1 + assert im.compare(im3, 3.0) == 0 diff --git a/test/python_tests/images/pycairo/cairo-cairo-expected.pdf b/test/python_tests/images/pycairo/cairo-cairo-expected.pdf index 220a9b210283716c1665809a927e7b23323a8568..2d2d0dad90df81642c8d8f07a83db8b809042c9f 100644 GIT binary patch literal 8148 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 E0juHt#Q*>R literal 4340 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 Date: Mon, 30 Jan 2023 11:53:59 +0000 Subject: [PATCH 05/37] convert more unit tests to use pytest [WIP] --- test/python_tests/copy_test.py | 84 +-- test/python_tests/csv_test.py | 632 ++++++++---------- test/python_tests/datasource_test.py | 172 ++--- .../datasource_xml_template_test.py | 37 +- test/python_tests/extra_map_props_test.py | 62 +- test/python_tests/feature_test.py | 93 ++- test/python_tests/filter_test.py | 316 ++++----- test/python_tests/fontset_test.py | 33 +- test/python_tests/geojson_plugin_test.py | 138 ++-- test/python_tests/geometry_io_test.py | 70 +- test/python_tests/grayscale_test.py | 10 +- .../python_tests/image_encoding_speed_test.py | 19 - 12 files changed, 713 insertions(+), 953 deletions(-) diff --git a/test/python_tests/copy_test.py b/test/python_tests/copy_test.py index b4aa45db2..d08a21d0a 100644 --- a/test/python_tests/copy_test.py +++ b/test/python_tests/copy_test.py @@ -1,21 +1,5 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_image_16_8_simple(): im = mapnik.Image(2, 2, mapnik.ImageType.gray16) im.set_pixel(0, 0, 256) @@ -23,16 +7,16 @@ def test_image_16_8_simple(): im.set_pixel(1, 0, 5) im.set_pixel(1, 1, 2) im2 = im.copy(mapnik.ImageType.gray8) - eq_(im2.get_pixel(0, 0), 255) - eq_(im2.get_pixel(0, 1), 255) - eq_(im2.get_pixel(1, 0), 5) - eq_(im2.get_pixel(1, 1), 2) + assert im2.get_pixel(0, 0) == 255 + assert im2.get_pixel(0, 1) == 255 + assert im2.get_pixel(1, 0) == 5 + assert im2.get_pixel(1, 1) == 2 # Cast back! im = im2.copy(mapnik.ImageType.gray16) - eq_(im.get_pixel(0, 0), 255) - eq_(im.get_pixel(0, 1), 255) - eq_(im.get_pixel(1, 0), 5) - eq_(im.get_pixel(1, 1), 2) + assert im.get_pixel(0, 0) == 255 + assert im.get_pixel(0, 1) == 255 + assert im.get_pixel(1, 0) == 5 + assert im.get_pixel(1, 1) == 2 def test_image_32f_8_simple(): @@ -42,20 +26,20 @@ def test_image_32f_8_simple(): im.set_pixel(1, 0, 120.6) im.set_pixel(1, 1, 360.2) im2 = im.copy(mapnik.ImageType.gray8) - eq_(im2.get_pixel(0, 0), 120) - eq_(im2.get_pixel(0, 1), 0) - eq_(im2.get_pixel(1, 0), 120) # Notice this is truncated! - eq_(im2.get_pixel(1, 1), 255) + assert im2.get_pixel(0, 0) == 120 + assert im2.get_pixel(0, 1) == 0 + assert im2.get_pixel(1, 0) == 120 # Notice this is truncated! + assert im2.get_pixel(1, 1) == 255 def test_image_offset_and_scale(): im = mapnik.Image(2, 2, mapnik.ImageType.gray16) - eq_(im.offset, 0.0) - eq_(im.scaling, 1.0) + assert im.offset == 0.0 + assert im.scaling == 1.0 im.offset = 1.0 im.scaling = 2.0 - eq_(im.offset, 1.0) - eq_(im.scaling, 2.0) + assert im.offset == 1.0 + assert im.scaling == 2.0 def test_image_16_8_scale_and_offset(): @@ -67,17 +51,17 @@ def test_image_16_8_scale_and_offset(): offset = 255 scaling = 3 im2 = im.copy(mapnik.ImageType.gray8, offset, scaling) - eq_(im2.get_pixel(0, 0), 0) - eq_(im2.get_pixel(0, 1), 1) - eq_(im2.get_pixel(1, 0), 255) - eq_(im2.get_pixel(1, 1), 120) + assert im2.get_pixel(0, 0) == 0 + assert im2.get_pixel(0, 1) == 1 + assert im2.get_pixel(1, 0) == 255 + assert im2.get_pixel(1, 1) == 120 # pixels will be a little off due to offsets in reverting! im3 = im2.copy(mapnik.ImageType.gray16) - eq_(im3.get_pixel(0, 0), 255) # Rounding error with ints - eq_(im3.get_pixel(0, 1), 258) # same + assert im3.get_pixel(0, 0) == 255 # Rounding error with ints + assert im3.get_pixel(0, 1) == 258 # same # The other one was way out of range for our scale/offset - eq_(im3.get_pixel(1, 0), 1020) - eq_(im3.get_pixel(1, 1), 615) # same + assert im3.get_pixel(1, 0) == 1020 + assert im3.get_pixel(1, 1) == 615 # same def test_image_16_32f_scale_and_offset(): @@ -89,16 +73,12 @@ def test_image_16_32f_scale_and_offset(): offset = 255 scaling = 3.2 im2 = im.copy(mapnik.ImageType.gray32f, offset, scaling) - eq_(im2.get_pixel(0, 0), 0.3125) - eq_(im2.get_pixel(0, 1), 0.9375) - eq_(im2.get_pixel(1, 0), -79.6875) - eq_(im2.get_pixel(1, 1), 112.5) + assert im2.get_pixel(0, 0) == 0.3125 + assert im2.get_pixel(0, 1) == 0.9375 + assert im2.get_pixel(1, 0) == -79.6875 + assert im2.get_pixel(1, 1) == 112.5 im3 = im2.copy(mapnik.ImageType.gray16) - eq_(im3.get_pixel(0, 0), 256) - eq_(im3.get_pixel(0, 1), 258) - eq_(im3.get_pixel(1, 0), 0) - eq_(im3.get_pixel(1, 1), 615) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im3.get_pixel(0, 0) == 256 + assert im3.get_pixel(0, 1) == 258 + assert im3.get_pixel(1, 0) == 0 + assert im3.get_pixel(1, 1) == 615 diff --git a/test/python_tests/csv_test.py b/test/python_tests/csv_test.py index 5f131b3d3..07c681cfa 100644 --- a/test/python_tests/csv_test.py +++ b/test/python_tests/csv_test.py @@ -1,45 +1,20 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -from __future__ import print_function - import glob import os - -from nose.tools import eq_, raises - import mapnik - -from .utilities import execution_path - - -default_logging_severity = mapnik.logger.get_severity() - - -def setup(): - # make the tests silent since we intentially test error conditions that - # are noisy - mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - -def teardown(): - mapnik.logger.set_severity(default_logging_severity) +import pytest if 'csv' in mapnik.DatasourceCache.plugin_names(): def get_csv_ds(filename): return mapnik.Datasource( - type='csv', file=os.path.join('../data/csv/', filename)) + type='csv', file=os.path.join('./test/data/csv/', filename)) def test_broken_files(visual=False): - broken = glob.glob("../data/csv/fails/*.*") - broken.extend(glob.glob("../data/csv/warns/*.*")) + broken = glob.glob("./test/data/csv/fails/*.*") + broken.extend(glob.glob("./test/data/csv/warns/*.*")) # Add a filename that doesn't exist - broken.append("../data/csv/fails/does_not_exist.csv") + broken.append("./test/data/csv/fails/does_not_exist.csv") for csv in broken: if visual: @@ -50,9 +25,10 @@ def test_broken_files(visual=False): print('\x1b[1;32m✓ \x1b[0m', csv) def test_good_files(visual=False): - good_files = glob.glob("../data/csv/*.*") - good_files.extend(glob.glob("../data/csv/warns/*.*")) - ignorable = os.path.join('..', 'data', 'csv', 'long_lat.vrt') + good_files = glob.glob("./test/data/csv/*.*") + good_files.extend(glob.glob("./test/data/csv/warns/*.*")) + ignorable = os.path.join('./test', 'data', 'csv', 'long_lat.vrt') + print("ignorable:", ignorable) good_files.remove(ignorable) for f in good_files: if f.endswith('.index'): @@ -70,46 +46,45 @@ def test_good_files(visual=False): def test_lon_lat_detection(**kwargs): ds = get_csv_ds('lon_lat.csv') - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['lon', 'lat']) - eq_(ds.field_types(), ['int', 'int']) + assert len(ds.fields()) == 2 + assert ds.fields(), ['lon' == 'lat'] + assert ds.field_types(), ['int' == 'int'] query = mapnik.Query(ds.envelope()) for fld in ds.fields(): query.add_property_name(fld) fs = ds.features(query) desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point feat = fs.next() attr = {'lon': 0, 'lat': 0} - eq_(feat.attributes, attr) + assert feat.attributes == attr def test_lng_lat_detection(**kwargs): ds = get_csv_ds('lng_lat.csv') - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['lng', 'lat']) - eq_(ds.field_types(), ['int', 'int']) + assert len(ds.fields()) == 2 + assert ds.fields(), ['lng' == 'lat'] + assert ds.field_types(), ['int' == 'int'] query = mapnik.Query(ds.envelope()) for fld in ds.fields(): query.add_property_name(fld) fs = ds.features(query) desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point feat = fs.next() attr = {'lng': 0, 'lat': 0} - eq_(feat.attributes, attr) + assert feat.attributes == attr def test_type_detection(**kwargs): ds = get_csv_ds('nypd.csv') - eq_(ds.fields(), - ['Precinct', - 'Phone', - 'Address', - 'City', - 'geo_longitude', - 'geo_latitude', - 'geo_accuracy']) - eq_(ds.field_types(), ['str', 'str', - 'str', 'str', 'float', 'float', 'str']) + assert ds.fields() == ['Precinct', + 'Phone', + 'Address', + 'City', + 'geo_longitude', + 'geo_latitude', + 'geo_accuracy'] + assert ds.field_types() == ['str', 'str', + 'str', 'str', 'float', 'float', 'str'] feat = ds.featureset().next() attr = { 'City': u'New York, NY', @@ -119,33 +94,33 @@ def test_type_detection(**kwargs): 'Precinct': u'5th Precinct', 'geo_longitude': -70, 'geo_latitude': 40} - eq_(feat.attributes, attr) - eq_(len(list(ds.all_features())), 2) + assert feat.attributes == attr + assert len(list(ds.all_features())) == 2 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_skipping_blank_rows(**kwargs): ds = get_csv_ds('blank_rows.csv') - eq_(ds.fields(), ['x', 'y', 'name']) - eq_(ds.field_types(), ['int', 'int', 'str']) - eq_(len(list(ds.all_features())), 2) + assert ds.fields(), ['x', 'y' == 'name'] + assert ds.field_types(), ['int', 'int' == 'str'] + assert len(list(ds.all_features())) == 2 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_empty_rows(**kwargs): ds = get_csv_ds('empty_rows.csv') - eq_(len(ds.fields()), 10) - eq_(len(ds.field_types()), 10) - eq_(ds.fields(), ['x', 'y', 'text', 'date', 'integer', - 'boolean', 'float', 'time', 'datetime', 'empty_column']) - eq_(ds.field_types(), ['int', 'int', 'str', 'str', - 'int', 'bool', 'float', 'str', 'str', 'str']) + assert len(ds.fields()) == 10 + assert len(ds.field_types()) == 10 + assert ds.fields() == ['x', 'y', 'text', 'date', 'integer', + 'boolean', 'float', 'time', 'datetime', 'empty_column'] + assert ds.field_types() == ['int', 'int', 'str', 'str', + 'int', 'bool', 'float', 'str', 'str', 'str'] fs = ds.featureset() attr = { 'x': 0, @@ -162,146 +137,138 @@ def test_empty_rows(**kwargs): for feat in fs: if first: first = False - eq_(feat.attributes, attr) - eq_(len(feat), 10) - eq_(feat['empty_column'], u'') + assert feat.attributes == attr + assert len(feat) == 10 + assert feat['empty_column'] == u'' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_slashes(**kwargs): ds = get_csv_ds('has_attributes_with_slashes.csv') - eq_(len(ds.fields()), 3) + assert len(ds.fields()) == 3 fs = list(ds.all_features()) - eq_(fs[0].attributes, {'x': 0, 'y': 0, 'name': u'a/a'}) - eq_(fs[1].attributes, {'x': 1, 'y': 4, 'name': u'b/b'}) - eq_(fs[2].attributes, {'x': 10, 'y': 2.5, 'name': u'c/c'}) + assert fs[0].attributes == {'x': 0, 'y': 0, 'name': u'a/a'} + assert fs[1].attributes == {'x': 1, 'y': 4, 'name': u'b/b'} + assert fs[2].attributes == {'x': 10, 'y': 2.5, 'name': u'c/c'} desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_wkt_field(**kwargs): ds = get_csv_ds('wkt.csv') - eq_(len(ds.fields()), 1) - eq_(ds.fields(), ['type']) - eq_(ds.field_types(), ['str']) + assert len(ds.fields()) == 1 + assert ds.fields() == ['type'] + assert ds.field_types() == ['str'] fs = list(ds.all_features()) - # eq_(len(fs[0].geometries()),1) - eq_(fs[0].geometry.type(), mapnik.GeometryType.Point) - # eq_(len(fs[1].geometries()),1) - eq_(fs[1].geometry.type(), mapnik.GeometryType.LineString) - # eq_(len(fs[2].geometries()),1) - eq_(fs[2].geometry.type(), mapnik.GeometryType.Polygon) - # eq_(len(fs[3].geometries()),1) # one geometry, two parts - eq_(fs[3].geometry.type(), mapnik.GeometryType.Polygon) - # eq_(len(fs[4].geometries()),4) - eq_(fs[4].geometry.type(), mapnik.GeometryType.MultiPoint) - # eq_(len(fs[5].geometries()),2) - eq_(fs[5].geometry.type(), mapnik.GeometryType.MultiLineString) - # eq_(len(fs[6].geometries()),2) - eq_(fs[6].geometry.type(), mapnik.GeometryType.MultiPolygon) - # eq_(len(fs[7].geometries()),2) - eq_(fs[7].geometry.type(), mapnik.GeometryType.MultiPolygon) + assert fs[0].geometry.type() == mapnik.GeometryType.Point + assert fs[1].geometry.type() == mapnik.GeometryType.LineString + assert fs[2].geometry.type() == mapnik.GeometryType.Polygon + assert fs[3].geometry.type() == mapnik.GeometryType.Polygon + assert fs[4].geometry.type() == mapnik.GeometryType.MultiPoint + assert fs[5].geometry.type() == mapnik.GeometryType.MultiLineString + assert fs[6].geometry.type() == mapnik.GeometryType.MultiPolygon + assert fs[7].geometry.type() == mapnik.GeometryType.MultiPolygon desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Collection) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Collection + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_handling_of_missing_header(**kwargs): ds = get_csv_ds('missing_header.csv') - eq_(len(ds.fields()), 6) - eq_(ds.fields(), ['one', 'two', 'x', 'y', '_4', 'aftermissing']) + assert len(ds.fields()) == 6 + assert ds.fields() == ['one', 'two', 'x', 'y', '_4', 'aftermissing'] fs = ds.featureset() feat = fs.next() - eq_(feat['_4'], 'missing') + assert feat['_4'] == 'missing' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_handling_of_headers_that_are_numbers(**kwargs): ds = get_csv_ds('numbers_for_headers.csv') - eq_(len(ds.fields()), 5) - eq_(ds.fields(), ['x', 'y', '1990', '1991', '1992']) + assert len(ds.fields()) == 5 + assert ds.fields() == ['x', 'y', '1990', '1991', '1992'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['1990'], 1) - eq_(feat['1991'], 2) - eq_(feat['1992'], 3) - eq_(mapnik.Expression("[1991]=2").evaluate(feat), True) + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['1990'] == 1 + assert feat['1991'] == 2 + assert feat['1992'] == 3 + assert mapnik.Expression("[1991]=2").evaluate(feat) def test_quoted_numbers(**kwargs): ds = get_csv_ds('points.csv') - eq_(len(ds.fields()), 6) - eq_(ds.fields(), ['lat', 'long', 'name', 'nr', 'color', 'placements']) + assert len(ds.fields()) == 6 + assert ds.fields(), ['lat', 'long', 'name', 'nr', 'color' == 'placements'] fs = list(ds.all_features()) - eq_(fs[0]['placements'], "N,S,E,W,SW,10,5") - eq_(fs[1]['placements'], "N,S,E,W,SW,10,5") - eq_(fs[2]['placements'], "N,S,E,W,SW,10,5") - eq_(fs[3]['placements'], "N,S,E,W,SW,10,5") - eq_(fs[4]['placements'], "N,S,E,W,SW,10,5") + assert fs[0]['placements'] == "N,S,E,W,SW,10,5" + assert fs[1]['placements'] == "N,S,E,W,SW,10,5" + assert fs[2]['placements'] == "N,S,E,W,SW,10,5" + assert fs[3]['placements'] == "N,S,E,W,SW,10,5" + assert fs[4]['placements'] == "N,S,E,W,SW,10,5" desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_reading_windows_newlines(**kwargs): ds = get_csv_ds('windows_newlines.csv') - eq_(len(ds.fields()), 3) + assert len(ds.fields()) == 3 feats = list(ds.all_features()) - eq_(len(feats), 1) + assert len(feats) == 1 fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 1) - eq_(feat['y'], 10) - eq_(feat['z'], 9999.9999) + assert feat['x'] == 1 + assert feat['y'] == 10 + assert feat['z'] == 9999.9999 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_reading_mac_newlines(**kwargs): ds = get_csv_ds('mac_newlines.csv') - eq_(len(ds.fields()), 3) + assert len(ds.fields()) == 3 feats = list(ds.all_features()) - eq_(len(feats), 1) + assert len(feats) == 1 fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 1) - eq_(feat['y'], 10) - eq_(feat['z'], 9999.9999) + assert feat['x'] == 1 + assert feat['y'] == 10 + assert feat['z'] == 9999.9999 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def check_newlines(filename): ds = get_csv_ds(filename) - eq_(len(ds.fields()), 3) + assert len(ds.fields()) == 3 feats = list(ds.all_features()) - eq_(len(feats), 1) + assert len(feats) == 1 fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['line'], 'many\n lines\n of text\n with unix newlines') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['line'] == 'many\n lines\n of text\n with unix newlines' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_mixed_mac_unix_newlines(**kwargs): check_newlines('mac_newlines_with_unix_inline.csv') @@ -325,111 +292,112 @@ def test_mixed_windows_unix_newlines_escaped(**kwargs): def test_tabs(**kwargs): ds = get_csv_ds('tabs_in_csv.csv') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'z']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'z'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], -122) - eq_(feat['y'], 48) - eq_(feat['z'], 0) + assert feat['x'] == -122 + assert feat['y'] == 48 + assert feat['z'] == 0 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_separator_pipes(**kwargs): ds = get_csv_ds('pipe_delimiters.csv') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'z']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'z'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['z'], 'hello') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['z'] == 'hello' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_separator_semicolon(**kwargs): ds = get_csv_ds('semicolon_delimiters.csv') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'z']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'z'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['z'], 'hello') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['z'] == 'hello' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_that_null_and_bool_keywords_are_empty_strings(**kwargs): ds = get_csv_ds('nulls_and_booleans_as_strings.csv') - eq_(len(ds.fields()), 4) - eq_(ds.fields(), ['x', 'y', 'null', 'boolean']) - eq_(ds.field_types(), ['int', 'int', 'str', 'bool']) + assert len(ds.fields()) == 4 + assert ds.fields(), ['x', 'y', 'null' == 'boolean'] + assert ds.field_types(), ['int', 'int', 'str' == 'bool'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['null'], 'null') - eq_(feat['boolean'], True) + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['null'] == 'null' + assert feat['boolean'] == True feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['null'], '') - eq_(feat['boolean'], False) + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['null'] == '' + assert feat['boolean'] == False desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point - @raises(RuntimeError) def test_that_nonexistant_query_field_throws(**kwargs): - ds = get_csv_ds('lon_lat.csv') - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['lon', 'lat']) - eq_(ds.field_types(), ['int', 'int']) - query = mapnik.Query(ds.envelope()) - for fld in ds.fields(): - query.add_property_name(fld) - # also add an invalid one, triggering throw - query.add_property_name('bogus') - ds.features(query) + with pytest.raises(RuntimeError): + ds = get_csv_ds('lon_lat.csv') + assert len(ds.fields()) == 2 + assert ds.fields(), ['lon' == 'lat'] + assert ds.field_types(), ['int' == 'int'] + query = mapnik.Query(ds.envelope()) + for fld in ds.fields(): + query.add_property_name(fld) + # also add an invalid one, triggering throw + query.add_property_name('bogus') + ds.features(query) + def test_that_leading_zeros_mean_strings(**kwargs): ds = get_csv_ds('leading_zeros.csv') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'fips']) - eq_(ds.field_types(), ['int', 'int', 'str']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'fips'] + assert ds.field_types(), ['int', 'int' == 'str'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['fips'], '001') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['fips'] == '001' feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['fips'], '003') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['fips'] == '003' feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['fips'], '005') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['fips'] == '005' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point def test_advanced_geometry_detection(**kwargs): ds = get_csv_ds('point_wkt.csv') - eq_(ds.describe()['geometry_type'], mapnik.DataGeometryType.Point) + assert ds.describe()['geometry_type'] == mapnik.DataGeometryType.Point ds = get_csv_ds('poly_wkt.csv') - eq_(ds.describe()['geometry_type'], mapnik.DataGeometryType.Polygon) + assert ds.describe()['geometry_type'] == mapnik.DataGeometryType.Polygon ds = get_csv_ds('multi_poly_wkt.csv') - eq_(ds.describe()['geometry_type'], mapnik.DataGeometryType.Polygon) + assert ds.describe()['geometry_type'] == mapnik.DataGeometryType.Polygon ds = get_csv_ds('line_wkt.csv') - eq_(ds.describe()['geometry_type'], mapnik.DataGeometryType.LineString) + assert ds.describe()['geometry_type'] == mapnik.DataGeometryType.LineString def test_creation_of_csv_from_in_memory_string(**kwargs): csv_string = ''' @@ -437,10 +405,10 @@ def test_creation_of_csv_from_in_memory_string(**kwargs): "POINT (120.15 48.47)","Winthrop, WA" ''' # csv plugin will test lines <= 10 chars for being fully blank ds = mapnik.Datasource(**{"type": "csv", "inline": csv_string}) - eq_(ds.describe()['geometry_type'], mapnik.DataGeometryType.Point) + assert ds.describe()['geometry_type'] == mapnik.DataGeometryType.Point fs = ds.featureset() feat = fs.next() - eq_(feat['Name'], u"Winthrop, WA") + assert feat['Name'], u"Winthrop == WA" def test_creation_of_csv_from_in_memory_string_with_uft8(**kwargs): csv_string = ''' @@ -448,37 +416,29 @@ def test_creation_of_csv_from_in_memory_string_with_uft8(**kwargs): "POINT (120.15 48.47)","Québec" ''' # csv plugin will test lines <= 10 chars for being fully blank ds = mapnik.Datasource(**{"type": "csv", "inline": csv_string}) - eq_(ds.describe()['geometry_type'], mapnik.DataGeometryType.Point) + assert ds.describe()['geometry_type'] == mapnik.DataGeometryType.Point fs = ds.featureset() feat = fs.next() - eq_(feat['Name'], u"Québec") + assert feat['Name'] == u"Québec" def validate_geojson_datasource(ds): - eq_(len(ds.fields()), 1) - eq_(ds.fields(), ['type']) - eq_(ds.field_types(), ['str']) + assert len(ds.fields()) == 1 + assert ds.fields() == ['type'] + assert ds.field_types() == ['str'] fs = list(ds.all_features()) - # eq_(len(fs[0].geometries()),1) - eq_(fs[0].geometry.type(), mapnik.GeometryType.Point) - # eq_(len(fs[1].geometries()),1) - eq_(fs[1].geometry.type(), mapnik.GeometryType.LineString) - # eq_(len(fs[2].geometries()),1) - eq_(fs[2].geometry.type(), mapnik.GeometryType.Polygon) - # eq_(len(fs[3].geometries()),1) # one geometry, two parts - eq_(fs[3].geometry.type(), mapnik.GeometryType.Polygon) - # eq_(len(fs[4].geometries()),4) - eq_(fs[4].geometry.type(), mapnik.GeometryType.MultiPoint) - # eq_(len(fs[5].geometries()),2) - eq_(fs[5].geometry.type(), mapnik.GeometryType.MultiLineString) - # eq_(len(fs[6].geometries()),2) - eq_(fs[6].geometry.type(), mapnik.GeometryType.MultiPolygon) - # eq_(len(fs[7].geometries()),2) - eq_(fs[7].geometry.type(), mapnik.GeometryType.MultiPolygon) + assert fs[0].geometry.type() == mapnik.GeometryType.Point + assert fs[1].geometry.type() == mapnik.GeometryType.LineString + assert fs[2].geometry.type() == mapnik.GeometryType.Polygon + assert fs[3].geometry.type() == mapnik.GeometryType.Polygon + assert fs[4].geometry.type() == mapnik.GeometryType.MultiPoint + assert fs[5].geometry.type() == mapnik.GeometryType.MultiLineString + assert fs[6].geometry.type() == mapnik.GeometryType.MultiPolygon + assert fs[7].geometry.type() == mapnik.GeometryType.MultiPolygon desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Collection) - eq_(desc['name'], 'csv') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Collection + assert desc['name'] == 'csv' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_json_field1(**kwargs): ds = get_csv_ds('geojson_double_quote_escape.csv') @@ -494,129 +454,129 @@ def test_json_field3(**kwargs): def test_that_blank_undelimited_rows_are_still_parsed(**kwargs): ds = get_csv_ds('more_headers_than_column_values.csv') - eq_(len(ds.fields()), 0) - eq_(ds.fields(), []) - eq_(ds.field_types(), []) + assert len(ds.fields()) == 0 + assert ds.fields() == [] + assert ds.field_types() == [] fs = list(ds.featureset()) - eq_(len(fs), 0) + assert len(fs) == 0 desc = ds.describe() - eq_(desc['geometry_type'], None) + assert desc['geometry_type'] == None - @raises(RuntimeError) def test_that_fewer_headers_than_rows_throws(**kwargs): - # this has invalid header # so throw - get_csv_ds('more_column_values_than_headers.csv') + with pytest.raises(RuntimeError): + # this has invalid header # so throw + get_csv_ds('more_column_values_than_headers.csv') def test_that_feature_id_only_incremented_for_valid_rows(**kwargs): ds = mapnik.Datasource(type='csv', - file=os.path.join('../data/csv/warns', 'feature_id_counting.csv')) - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'id']) - eq_(ds.field_types(), ['int', 'int', 'int']) + file=os.path.join('./test/data/csv/warns', 'feature_id_counting.csv')) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'id'] + assert ds.field_types(), ['int', 'int' == 'int'] fs = ds.featureset() # first feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['id'], 1) + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['id'] == 1 # second, should have skipped bogus one feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['id'], 2) + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['id'] == 2 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(len(list(ds.all_features())), 2) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert len(list(ds.all_features())) == 2 def test_dynamically_defining_headers1(**kwargs): ds = mapnik.Datasource(type='csv', file=os.path.join( - '../data/csv/fails', 'needs_headers_two_lines.csv'), + './test/data/csv/fails', 'needs_headers_two_lines.csv'), headers='x,y,name') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'name']) - eq_(ds.field_types(), ['int', 'int', 'str']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'name'] + assert ds.field_types(), ['int', 'int' == 'str'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['name'], 'data_name') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['name'] == 'data_name' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(len(list(ds.all_features())), 2) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert len(list(ds.all_features())) == 2 def test_dynamically_defining_headers2(**kwargs): ds = mapnik.Datasource(type='csv', file=os.path.join( - '../data/csv/fails', 'needs_headers_one_line.csv'), + './test/data/csv/fails', 'needs_headers_one_line.csv'), headers='x,y,name') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'name']) - eq_(ds.field_types(), ['int', 'int', 'str']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'name'] + assert ds.field_types(), ['int', 'int' == 'str'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['name'], 'data_name') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['name'] == 'data_name' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(len(list(ds.all_features())), 1) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert len(list(ds.all_features())) == 1 def test_dynamically_defining_headers3(**kwargs): ds = mapnik.Datasource(type='csv', file=os.path.join( - '../data/csv/fails', 'needs_headers_one_line_no_newline.csv'), + './test/data/csv/fails', 'needs_headers_one_line_no_newline.csv'), headers='x,y,name') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'name']) - eq_(ds.field_types(), ['int', 'int', 'str']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'name'] + assert ds.field_types(), ['int', 'int' == 'str'] fs = ds.featureset() feat = fs.next() - eq_(feat['x'], 0) - eq_(feat['y'], 0) - eq_(feat['name'], 'data_name') + assert feat['x'] == 0 + assert feat['y'] == 0 + assert feat['name'] == 'data_name' desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(len(list(ds.all_features())), 1) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert len(list(ds.all_features())) == 1 def test_that_64bit_int_fields_work(**kwargs): ds = get_csv_ds('64bit_int.csv') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'bigint']) - eq_(ds.field_types(), ['int', 'int', 'int']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'bigint'] + assert ds.field_types(), ['int', 'int' == 'int'] fs = ds.featureset() feat = fs.next() - eq_(feat['bigint'], 2147483648) + assert feat['bigint'] == 2147483648 feat = fs.next() - eq_(feat['bigint'], 9223372036854775807) - eq_(feat['bigint'], 0x7FFFFFFFFFFFFFFF) + assert feat['bigint'] == 9223372036854775807 + assert feat['bigint'] == 0x7FFFFFFFFFFFFFFF desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(len(list(ds.all_features())), 2) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert len(list(ds.all_features())) == 2 def test_various_number_types(**kwargs): ds = get_csv_ds('number_types.csv') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['x', 'y', 'floats']) - eq_(ds.field_types(), ['int', 'int', 'float']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['x', 'y' == 'floats'] + assert ds.field_types(), ['int', 'int' == 'float'] fs = ds.featureset() feat = fs.next() - eq_(feat['floats'], .0) + assert feat['floats'] == .0 feat = fs.next() - eq_(feat['floats'], +.0) + assert feat['floats'] == +.0 feat = fs.next() - eq_(feat['floats'], 1e-06) + assert feat['floats'] == 1e-06 feat = fs.next() - eq_(feat['floats'], -1e-06) + assert feat['floats'] == -1e-06 feat = fs.next() - eq_(feat['floats'], 0.000001) + assert feat['floats'] == 0.000001 feat = fs.next() - eq_(feat['floats'], 1.234e+16) + assert feat['floats'] == 1.234e+16 feat = fs.next() - eq_(feat['floats'], 1.234e+16) + assert feat['floats'] == 1.234e+16 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(len(list(ds.all_features())), 8) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert len(list(ds.all_features())) == 8 def test_manually_supplied_extent(**kwargs): csv_string = ''' @@ -625,21 +585,17 @@ def test_manually_supplied_extent(**kwargs): ds = mapnik.Datasource( **{"type": "csv", "extent": "-180,-90,180,90", "inline": csv_string}) b = ds.envelope() - eq_(b.minx, -180) - eq_(b.miny, -90) - eq_(b.maxx, 180) - eq_(b.maxy, 90) + assert b.minx == -180 + assert b.miny == -90 + assert b.maxx == 180 + assert b.maxy == 90 def test_inline_geojson(**kwargs): csv_string = "geojson\n'{\"coordinates\":[-92.22568,38.59553],\"type\":\"Point\"}'" ds = mapnik.Datasource(**{"type": "csv", "inline": csv_string}) - eq_(len(ds.fields()), 0) - eq_(ds.fields(), []) - # FIXME - re-enable after https://github.com/mapnik/mapnik/issues/2319 is fixed - #fs = ds.featureset() - #feat = fs.next() - # eq_(feat.num_geometries(),1) - -if __name__ == "__main__": - setup() - [eval(run)(visual=True) for run in dir() if 'test_' in run] + assert len(ds.fields()) == 0 + assert ds.fields() == [] + fs = ds.featureset() + feat = fs.next() + assert feat.geometry.type() == mapnik.GeometryType.Point + assert feat.geometry.to_wkt() == "POINT(-92.22568 38.59553)" diff --git a/test/python_tests/datasource_test.py b/test/python_tests/datasource_test.py index 8a2183abb..5fa6780c6 100644 --- a/test/python_tests/datasource_test.py +++ b/test/python_tests/datasource_test.py @@ -1,160 +1,141 @@ -#!/usr/bin/env python import os import sys -from itertools import groupby - -from nose.tools import eq_, raises - import mapnik +import pytest -from .utilities import execution_path, run_all - -PYTHON3 = sys.version_info[0] == 3 -if PYTHON3: - xrange = range - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - +from itertools import groupby def test_that_datasources_exist(): if len(mapnik.DatasourceCache.plugin_names()) == 0: print('***NOTICE*** - no datasource plugins have been loaded') # adapted from raster_symboliser_test#test_dataraster_query_point - - -@raises(RuntimeError) def test_vrt_referring_to_missing_files(): - srs = 'epsg:32630' - if 'gdal' in mapnik.DatasourceCache.plugin_names(): - lyr = mapnik.Layer('dataraster') - lyr.datasource = mapnik.Gdal( - file='../data/raster/missing_raster.vrt', - band=1, - ) - lyr.srs = srs - _map = mapnik.Map(256, 256, srs) - _map.layers.append(lyr) - - # center of extent of raster - x, y = 556113.0, 4381428.0 # center of extent of raster - - _map.zoom_all() - - # Fancy stuff to supress output of error - # open 2 fds - null_fds = [os.open(os.devnull, os.O_RDWR) for x in xrange(2)] - # save the current file descriptors to a tuple - save = os.dup(1), os.dup(2) - # put /dev/null fds on 1 and 2 - os.dup2(null_fds[0], 1) - os.dup2(null_fds[1], 2) - - # *** run the function *** - try: - # Should RuntimeError here - list(_map.query_point(0, x, y)) - finally: - # restore file descriptors so I can print the results - os.dup2(save[0], 1) - os.dup2(save[1], 2) - # close the temporary fds - os.close(null_fds[0]) - os.close(null_fds[1]) + with pytest.raises(RuntimeError): + srs = 'epsg:32630' + if 'gdal' in mapnik.DatasourceCache.plugin_names(): + lyr = mapnik.Layer('dataraster') + lyr.datasource = mapnik.Gdal( + file='./test/data/raster/missing_raster.vrt', + band=1, + ) + lyr.srs = srs + _map = mapnik.Map(256, 256, srs) + _map.layers.append(lyr) + + # center of extent of raster + x, y = 556113.0, 4381428.0 # center of extent of raster + _map.zoom_all() + + # Fancy stuff to supress output of error + # open 2 fds + null_fds = [os.open(os.devnull, os.O_RDWR) for x in range(2)] + # save the current file descriptors to a tuple + save = os.dup(1), os.dup(2) + # put /dev/null fds on 1 and 2 + os.dup2(null_fds[0], 1) + os.dup2(null_fds[1], 2) + + # *** run the function *** + try: + # Should RuntimeError here + list(_map.query_point(0, x, y)) + finally: + # restore file descriptors so I can print the results + os.dup2(save[0], 1) + os.dup2(save[1], 2) + # close the temporary fds + os.close(null_fds[0]) + os.close(null_fds[1]) def test_field_listing(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='../data/shp/poly.shp') + ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') fields = ds.fields() - eq_(fields, ['AREA', 'EAS_ID', 'PRFEDEA']) + assert fields, ['AREA', 'EAS_ID' == 'PRFEDEA'] desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Polygon) - eq_(desc['name'], 'shape') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Polygon + assert desc['name'] == 'shape' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' def test_total_feature_count_shp(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='../data/shp/poly.shp') + ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') features = ds.all_features() num_feats = len(list(features)) - eq_(num_feats, 10) - + assert num_feats == 10 def test_total_feature_count_json(): if 'ogr' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Ogr(file='../data/json/points.geojson', layer_by_index=0) + ds = mapnik.Ogr(file='./test/data/json/points.geojson', layer_by_index=0) desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(desc['name'], 'ogr') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert desc['name'] == 'ogr' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' features = ds.all_features() num_feats = len(list(features)) - eq_(num_feats, 5) + assert num_feats == 5 def test_sqlite_reading(): if 'sqlite' in mapnik.DatasourceCache.plugin_names(): ds = mapnik.SQLite( - file='../data/sqlite/world.sqlite', + file='./test/data/sqlite/world.sqlite', table_by_index=0) desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Polygon) - eq_(desc['name'], 'sqlite') - eq_(desc['type'], mapnik.DataType.Vector) - eq_(desc['encoding'], 'utf-8') + assert desc['geometry_type'] == mapnik.DataGeometryType.Polygon + assert desc['name'] == 'sqlite' + assert desc['type'] == mapnik.DataType.Vector + assert desc['encoding'] == 'utf-8' features = ds.all_features() num_feats = len(list(features)) - eq_(num_feats, 245) + assert num_feats == 245 def test_reading_json_from_string(): - with open('../data/json/points.geojson', 'r') as f: + with open('./test/data/json/points.geojson', 'r') as f: json = f.read() if 'ogr' in mapnik.DatasourceCache.plugin_names(): ds = mapnik.Ogr(file=json, layer_by_index=0) features = ds.all_features() num_feats = len(list(features)) - eq_(num_feats, 5) + assert num_feats == 5 def test_feature_envelope(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='../data/shp/poly.shp') + ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') features = ds.all_features() for feat in features: env = feat.envelope() contains = ds.envelope().contains(env) - eq_(contains, True) + assert contains == True intersects = ds.envelope().contains(env) - eq_(intersects, True) + assert intersects == True def test_feature_attributes(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='../data/shp/poly.shp') + ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') features = list(ds.all_features()) feat = features[0] attrs = {'PRFEDEA': u'35043411', 'EAS_ID': 168, 'AREA': 215229.266} - eq_(feat.attributes, attrs) - eq_(ds.fields(), ['AREA', 'EAS_ID', 'PRFEDEA']) - eq_(ds.field_types(), ['float', 'int', 'str']) + assert feat.attributes == attrs + assert ds.fields(), ['AREA', 'EAS_ID' == 'PRFEDEA'] + assert ds.field_types(), ['float', 'int' == 'str'] def test_ogr_layer_by_sql(): if 'ogr' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Ogr(file='../data/shp/poly.shp', + ds = mapnik.Ogr(file='./test/data/shp/poly.shp', layer_by_sql='SELECT * FROM poly WHERE EAS_ID = 168') features = ds.all_features() num_feats = len(list(features)) - eq_(num_feats, 1) + assert num_feats == 1 def test_hit_grid(): @@ -166,12 +147,12 @@ def rle_encode(l): m = mapnik.Map(256, 256) try: - mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') + mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') m.zoom_all() join_field = 'NAME' fg = [] # feature grid - for y in xrange(0, 256, 4): - for x in xrange(0, 256, 4): + for y in range(0, 256, 4): + for x in range(0, 256, 4): featureset = m.query_map_point(0, x, y) added = False for feature in featureset: @@ -180,14 +161,9 @@ def rle_encode(l): if not added: fg.append('') hit_list = '|'.join(rle_encode(fg)) - eq_(hit_list[:16], '730:|2:Greenland') - eq_(hit_list[-12:], '1:Chile|812:') + assert hit_list[:16] == '730:|2:Greenland' + assert hit_list[-12:] == '1:Chile|812:' except RuntimeError as e: # only test datasources that we have installed if not 'Could not create datasource' in str(e): raise RuntimeError(str(e)) - - -if __name__ == '__main__': - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) diff --git a/test/python_tests/datasource_xml_template_test.py b/test/python_tests/datasource_xml_template_test.py index b561d93e6..1a0c06131 100644 --- a/test/python_tests/datasource_xml_template_test.py +++ b/test/python_tests/datasource_xml_template_test.py @@ -1,27 +1,18 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_datasource_template_is_working(): m = mapnik.Map(256, 256) - try: - mapnik.load_map(m, '../data/good_maps/datasource.xml') - except RuntimeError as e: - if "Required parameter 'type'" in str(e): - raise RuntimeError(e) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + mapnik.load_map(m, './test/data/good_maps/datasource.xml') + for layer in m.layers: + layer_bbox = layer.envelope() + bbox = None + first = True + for feature in layer.datasource: + assert feature.envelope() == feature.geometry.envelope() + assert layer_bbox.contains(feature.envelope()) + if first: + first = False + bbox = feature.envelope() + else: + bbox += feature.envelope() + assert layer_bbox == bbox diff --git a/test/python_tests/extra_map_props_test.py b/test/python_tests/extra_map_props_test.py index ac9e7482d..1b8796763 100644 --- a/test/python_tests/extra_map_props_test.py +++ b/test/python_tests/extra_map_props_test.py @@ -1,48 +1,32 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_arbitrary_parameters_attached_to_map(): m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/extra_arbitary_map_parameters.xml') - eq_(len(m.parameters), 5) - eq_(m.parameters['key'], 'value2') - eq_(m.parameters['key3'], 'value3') - eq_(m.parameters['unicode'], u'iván') - eq_(m.parameters['integer'], 10) - eq_(m.parameters['decimal'], .999) + mapnik.load_map(m, './test/data/good_maps/extra_arbitary_map_parameters.xml') + assert len(m.parameters) == 5 + assert m.parameters['key'] == 'value2' + assert m.parameters['key3'] == 'value3' + assert m.parameters['unicode'] == u'iván' + assert m.parameters['integer'] == 10 + assert m.parameters['decimal'] == .999 m2 = mapnik.Map(256, 256) for k, v in m.parameters: m2.parameters.append(mapnik.Parameter(k, v)) - eq_(len(m2.parameters), 5) - eq_(m2.parameters['key'], 'value2') - eq_(m2.parameters['key3'], 'value3') - eq_(m2.parameters['unicode'], u'iván') - eq_(m2.parameters['integer'], 10) - eq_(m2.parameters['decimal'], .999) + assert len(m2.parameters) == 5 + assert m2.parameters['key'] == 'value2' + assert m2.parameters['key3'] == 'value3' + assert m2.parameters['unicode'] == u'iván' + assert m2.parameters['integer'] == 10 + assert m2.parameters['decimal'] == .999 map_string = mapnik.save_map_to_string(m) m3 = mapnik.Map(256, 256) mapnik.load_map_from_string(m3, map_string) - eq_(len(m3.parameters), 5) - eq_(m3.parameters['key'], 'value2') - eq_(m3.parameters['key3'], 'value3') - eq_(m3.parameters['unicode'], u'iván') - eq_(m3.parameters['integer'], 10) - eq_(m3.parameters['decimal'], .999) + assert len(m3.parameters) == 5 + assert m3.parameters['key'] == 'value2' + assert m3.parameters['key3'] == 'value3' + assert m3.parameters['unicode'] == u'iván' + assert m3.parameters['integer'] == 10 + assert m3.parameters['decimal'] == .999 def test_serializing_arbitrary_parameters(): @@ -52,9 +36,5 @@ def test_serializing_arbitrary_parameters(): m2 = mapnik.Map(1, 1) mapnik.load_map_from_string(m2, mapnik.save_map_to_string(m)) - eq_(m2.parameters['width'], m.width) - eq_(m2.parameters['height'], m.height) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert m2.parameters['width'] == m.width + assert m2.parameters['height'] == m.height diff --git a/test/python_tests/feature_test.py b/test/python_tests/feature_test.py index 7a544af1a..d4f8afc61 100644 --- a/test/python_tests/feature_test.py +++ b/test/python_tests/feature_test.py @@ -1,26 +1,17 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - from binascii import unhexlify - -from nose.tools import eq_, raises - import mapnik - -from .utilities import run_all - +import pytest def test_default_constructor(): f = mapnik.Feature(mapnik.Context(), 1) - eq_(f is not None, True) + assert f is not None def test_feature_geo_interface(): ctx = mapnik.Context() feat = mapnik.Feature(ctx, 1) feat.geometry = mapnik.Geometry.from_wkt('Point (0 0)') - eq_(feat.__geo_interface__['geometry'], { - u'type': u'Point', u'coordinates': [0, 0]}) + assert feat.__geo_interface__['geometry'] == {u'type': u'Point', u'coordinates': [0, 0]} def test_python_extended_constructor(): @@ -31,15 +22,15 @@ def test_python_extended_constructor(): wkt = 'POLYGON ((35 10, 10 20, 15 40, 45 45, 35 10),(20 30, 35 35, 30 20, 20 30))' f.geometry = mapnik.Geometry.from_wkt(wkt) f['foo'] = 'bar' - eq_(f['foo'], 'bar') - eq_(f.envelope(), mapnik.Box2d(10.0, 10.0, 45.0, 45.0)) + assert f['foo'] == 'bar' + assert f.envelope(), mapnik.Box2d(10.0, 10.0, 45.0 == 45.0) # reset f['foo'] = u"avión" - eq_(f['foo'], u"avión") + assert f['foo'] == u"avión" f['foo'] = 1.4 - eq_(f['foo'], 1.4) + assert f['foo'] == 1.4 f['foo'] = True - eq_(f['foo'], True) + assert f['foo'] == True def test_add_geom_wkb(): @@ -49,13 +40,13 @@ def test_add_geom_wkb(): if hasattr(geometry, 'is_valid'): # Those are only available when python-mapnik has been built with # boost >= 1.56. - eq_(geometry.is_valid(), True) - eq_(geometry.is_simple(), True) - eq_(geometry.envelope(), mapnik.Box2d(10.0, 10.0, 40.0, 40.0)) + assert geometry.is_valid() == True + assert geometry.is_simple() == True + assert geometry.envelope(), mapnik.Box2d(10.0, 10.0, 40.0 == 40.0) geometry.correct() if hasattr(geometry, 'is_valid'): # valid after calling correct - eq_(geometry.is_valid(), True) + assert geometry.is_valid() == True def test_feature_expression_evaluation(): @@ -63,13 +54,13 @@ def test_feature_expression_evaluation(): context.push('name') f = mapnik.Feature(context, 1) f['name'] = 'a' - eq_(f['name'], u'a') + assert f['name'] == u'a' expr = mapnik.Expression("[name]='a'") evaluated = expr.evaluate(f) - eq_(evaluated, True) + assert evaluated == True num_attributes = len(f) - eq_(num_attributes, 1) - eq_(f.id(), 1) + assert num_attributes == 1 + assert f.id() == 1 # https://github.com/mapnik/mapnik/issues/933 @@ -79,16 +70,16 @@ def test_feature_expression_evaluation_missing_attr(): context.push('name') f = mapnik.Feature(context, 1) f['name'] = u'a' - eq_(f['name'], u'a') + assert f['name'] == u'a' expr = mapnik.Expression("[fielddoesnotexist]='a'") - eq_('fielddoesnotexist' in f, False) + assert not 'fielddoesnotexist' in f try: expr.evaluate(f) except Exception as e: - eq_("Key does not exist" in str(e), True) + assert "Key does not exist" in str(e) == True num_attributes = len(f) - eq_(num_attributes, 1) - eq_(f.id(), 1) + assert num_attributes == 1 + assert f.id() == 1 # https://github.com/mapnik/mapnik/issues/934 @@ -98,31 +89,27 @@ def test_feature_expression_evaluation_attr_with_spaces(): context.push('name with space') f = mapnik.Feature(context, 1) f['name with space'] = u'a' - eq_(f['name with space'], u'a') + assert f['name with space'] == u'a' expr = mapnik.Expression("[name with space]='a'") - eq_(str(expr), "([name with space]='a')") - eq_(expr.evaluate(f), True) + assert str(expr) == "([name with space]='a')" + assert expr.evaluate(f) == True # https://github.com/mapnik/mapnik/issues/2390 - -@raises(RuntimeError) def test_feature_from_geojson(): - ctx = mapnik.Context() - inline_string = """ - { - "geometry" : { - "coordinates" : [ 0,0 ] - "type" : "Point" - }, - "type" : "Feature", - "properties" : { - "this":"that" - "known":"nope because missing comma" - } - } - """ - mapnik.Feature.from_geojson(inline_string, ctx) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + with pytest.raises(RuntimeError): + ctx = mapnik.Context() + inline_string = """ + { + "geometry" : { + "coordinates" : [ 0,0 ] + "type" : "Point" + }, + "type" : "Feature", + "properties" : { + "this":"that" + "known":"nope because missing comma" + } + } + """ + mapnik.Feature.from_geojson(inline_string, ctx) diff --git a/test/python_tests/filter_test.py b/test/python_tests/filter_test.py index 39deb5b2f..641d6950f 100644 --- a/test/python_tests/filter_test.py +++ b/test/python_tests/filter_test.py @@ -1,18 +1,5 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- -import sys - -from nose.tools import eq_, raises - import mapnik - -from .utilities import run_all - -PYTHON3 = sys.version_info[0] == 3 -if PYTHON3: - long = int - unicode = str - +import pytest if hasattr(mapnik, 'Expression'): mapnik.Filter = mapnik.Expression @@ -96,11 +83,11 @@ def test_filter_init(): first = filters[0] for f in filters: - eq_(str(first), str(f)) + assert str(first) == str(f) s = m.find_style('s2') - eq_(s.filter_mode, mapnik.filter_mode.FIRST) + assert s.filter_mode == mapnik.filter_mode.FIRST def test_geometry_type_eval(): @@ -110,45 +97,42 @@ def test_geometry_type_eval(): f = mapnik.Feature(context2, 0) f["mapnik::geometry_type"] = 'sneaky' expr = mapnik.Expression("[mapnik::geometry_type]") - eq_(expr.evaluate(f), 0) + assert expr.evaluate(f) == 0 expr = mapnik.Expression("[mapnik::geometry_type]") context = mapnik.Context() # no geometry f = mapnik.Feature(context, 0) - eq_(expr.evaluate(f), 0) - eq_(mapnik.Expression("[mapnik::geometry_type]=0").evaluate(f), True) + assert expr.evaluate(f) == 0 + assert mapnik.Expression("[mapnik::geometry_type]=0").evaluate(f) # POINT = 1 f = mapnik.Feature(context, 0) f.geometry = mapnik.Geometry.from_wkt('POINT(10 40)') - eq_(expr.evaluate(f), 1) - eq_(mapnik.Expression("[mapnik::geometry_type]=point").evaluate(f), True) + assert expr.evaluate(f) == 1 + assert mapnik.Expression("[mapnik::geometry_type]=point").evaluate(f) # LINESTRING = 2 f = mapnik.Feature(context, 0) f.geometry = mapnik.Geometry.from_wkt('LINESTRING (30 10, 10 30, 40 40)') - eq_(expr.evaluate(f), 2) - eq_(mapnik.Expression( - "[mapnik::geometry_type] = linestring").evaluate(f), True) + assert expr.evaluate(f) == 2 + assert mapnik.Expression("[mapnik::geometry_type] = linestring").evaluate(f) # POLYGON = 3 f = mapnik.Feature(context, 0) f.geometry = mapnik.Geometry.from_wkt( 'POLYGON ((30 10, 10 20, 20 40, 40 40, 30 10))') - eq_(expr.evaluate(f), 3) - eq_(mapnik.Expression( - "[mapnik::geometry_type] = polygon").evaluate(f), True) + assert expr.evaluate(f) == 3 + assert mapnik.Expression("[mapnik::geometry_type] = polygon").evaluate(f) # COLLECTION = 4 f = mapnik.Feature(context, 0) geom = mapnik.Geometry.from_wkt( 'GEOMETRYCOLLECTION(POLYGON((1 1,2 1,2 2,1 2,1 1)),POINT(2 3),LINESTRING(2 3,3 4))') f.geometry = geom - eq_(expr.evaluate(f), 4) - eq_(mapnik.Expression( - "[mapnik::geometry_type] = collection").evaluate(f), True) + assert expr.evaluate(f) == 4 + assert mapnik.Expression("[mapnik::geometry_type] = collection").evaluate(f) def test_regex_match(): @@ -157,7 +141,7 @@ def test_regex_match(): f = mapnik.Feature(context, 0) f["name"] = 'test' expr = mapnik.Expression("[name].match('test')") - eq_(expr.evaluate(f), True) # 1 == True + assert expr.evaluate(f) # 1 == True def test_unicode_regex_match(): @@ -166,7 +150,7 @@ def test_unicode_regex_match(): f = mapnik.Feature(context, 0) f["name"] = 'Québec' expr = mapnik.Expression("[name].match('Québec')") - eq_(expr.evaluate(f), True) # 1 == True + assert expr.evaluate(f) # 1 == True def test_regex_replace(): @@ -175,12 +159,12 @@ def test_regex_replace(): f = mapnik.Feature(context, 0) f["name"] = 'test' expr = mapnik.Expression("[name].replace('(\\B)|( )','$1 ')") - eq_(expr.evaluate(f), 't e s t') + assert expr.evaluate(f) == 't e s t' def test_unicode_regex_replace_to_str(): expr = mapnik.Expression("[name].replace('(\\B)|( )','$1 ')") - eq_(str(expr), "[name].replace('(\\B)|( )','$1 ')") + assert str(expr), "[name].replace('(\\B)|( )' == '$1 ')" def test_unicode_regex_replace(): @@ -190,7 +174,7 @@ def test_unicode_regex_replace(): f["name"] = 'Québec' expr = mapnik.Expression("[name].replace('(\\B)|( )','$1 ')") # will fail if -DBOOST_REGEX_HAS_ICU is not defined - eq_(expr.evaluate(f), u'Q u é b e c') + assert expr.evaluate(f) == u'Q u é b e c' def test_float_precision(): @@ -199,16 +183,16 @@ def test_float_precision(): f = mapnik.Feature(context, 0) f["num1"] = 1.0000 f["num2"] = 1.0001 - eq_(f["num1"], 1.0000) - eq_(f["num2"], 1.0001) + assert f["num1"] == 1.0000 + assert f["num2"] == 1.0001 expr = mapnik.Expression("[num1] = 1.0000") - eq_(expr.evaluate(f), True) + assert expr.evaluate(f) expr = mapnik.Expression("[num1].match('1')") - eq_(expr.evaluate(f), True) + assert expr.evaluate(f) expr = mapnik.Expression("[num2] = 1.0001") - eq_(expr.evaluate(f), True) + assert expr.evaluate(f) expr = mapnik.Expression("[num2].match('1.0001')") - eq_(expr.evaluate(f), True) + assert expr.evaluate(f) def test_string_matching_on_precision(): @@ -216,9 +200,9 @@ def test_string_matching_on_precision(): context.push('num') f = mapnik.Feature(context, 0) f["num"] = "1.0000" - eq_(f["num"], "1.0000") + assert f["num"] == "1.0000" expr = mapnik.Expression("[num].match('.*(^0|00)$')") - eq_(expr.evaluate(f), True) + assert expr.evaluate(f) def test_creation_of_null_value(): @@ -226,12 +210,12 @@ def test_creation_of_null_value(): context.push('nv') f = mapnik.Feature(context, 0) f["nv"] = None - eq_(f["nv"], None) - eq_(f["nv"] is None, True) + assert f["nv"] == None + assert f["nv"] is None # test boolean f["nv"] = 0 - eq_(f["nv"], 0) - eq_(f["nv"] is not None, True) + assert f["nv"] == 0 + assert f["nv"] is not None def test_creation_of_bool(): @@ -239,39 +223,39 @@ def test_creation_of_bool(): context.push('bool') f = mapnik.Feature(context, 0) f["bool"] = True - eq_(f["bool"], True) + assert f["bool"] # TODO - will become int of 1 do to built in boost python conversion # https://github.com/mapnik/mapnik/issues/1873 - eq_(isinstance(f["bool"], bool) or isinstance(f["bool"], long), True) + assert isinstance(f["bool"], bool) or isinstance(f["bool"], int) f["bool"] = False - eq_(f["bool"], False) - eq_(isinstance(f["bool"], bool) or isinstance(f["bool"], long), True) + assert f["bool"] == False + assert isinstance(f["bool"], bool) or isinstance(f["bool"], int) # test NoneType f["bool"] = None - eq_(f["bool"], None) - eq_(isinstance(f["bool"], bool) or isinstance(f["bool"], long), False) + assert f["bool"] == None + assert not isinstance(f["bool"], bool) or isinstance(f["bool"], int) # test integer f["bool"] = 0 - eq_(f["bool"], 0) + assert f["bool"] == 0 # https://github.com/mapnik/mapnik/issues/1873 # ugh, boost_python's built into converter does not work right - # eq_(isinstance(f["bool"],bool),False) + # assert isinstance(f["bool"],bool) == False null_equality = [ - ['hello', False, unicode], - [u'', False, unicode], - [0, False, long], - [123, False, long], + ['hello', False, str], + [u'', False, str], + [0, False, int], + [123, False, int], [0.0, False, float], [123.123, False, float], [.1, False, float], # TODO - should become bool: https://github.com/mapnik/mapnik/issues/1873 - [False, False, long], + [False, False, int], # TODO - should become bool: https://github.com/mapnik/mapnik/issues/1873 - [True, False, long], + [True, False, int], [None, True, None], - [2147483648, False, long], - [922337203685477580, False, long] + [2147483648, False, int], + [922337203685477580, False, int] ] @@ -280,16 +264,15 @@ def test_expressions_with_null_equality(): context = mapnik.Context() f = mapnik.Feature(context, 0) f["prop"] = eq[0] - eq_(f["prop"], eq[0]) + assert f["prop"] == eq[0] if eq[0] is None: - eq_(f["prop"] is None, True) + assert f["prop"] is None else: - eq_(isinstance(f['prop'], eq[2]), True, - '%s is not an instance of %s' % (f['prop'], eq[2])) + assert isinstance(f['prop'], eq[2]), '%s is not an instance of %s' % (f['prop'], eq[2]) expr = mapnik.Expression("[prop] = null") - eq_(expr.evaluate(f), eq[1]) + assert expr.evaluate(f) == eq[1] expr = mapnik.Expression("[prop] is null") - eq_(expr.evaluate(f), eq[1]) + assert expr.evaluate(f) == eq[1] def test_expressions_with_null_equality2(): @@ -297,35 +280,34 @@ def test_expressions_with_null_equality2(): context = mapnik.Context() f = mapnik.Feature(context, 0) f["prop"] = eq[0] - eq_(f["prop"], eq[0]) + assert f["prop"] == eq[0] if eq[0] is None: - eq_(f["prop"] is None, True) + assert f["prop"] is None else: - eq_(isinstance(f['prop'], eq[2]), True, - '%s is not an instance of %s' % (f['prop'], eq[2])) + assert isinstance(f['prop'], eq[2]), '%s is not an instance of %s' % (f['prop'], eq[2]) # TODO - support `is not` syntax: # https://github.com/mapnik/mapnik/issues/796 expr = mapnik.Expression("not [prop] is null") - eq_(expr.evaluate(f), not eq[1]) + assert not expr.evaluate(f) == eq[1] # https://github.com/mapnik/mapnik/issues/1642 expr = mapnik.Expression("[prop] != null") - eq_(expr.evaluate(f), not eq[1]) + assert not expr.evaluate(f) == eq[1] truthyness = [ - [u'hello', True, unicode], - [u'', False, unicode], - [0, False, long], - [123, True, long], + [u'hello', True, str], + [u'', False, str], + [0, False, int], + [123, True, int], [0.0, False, float], [123.123, True, float], [.1, True, float], # TODO - should become bool: https://github.com/mapnik/mapnik/issues/1873 - [False, False, long], + [False, False, int], # TODO - should become bool: https://github.com/mapnik/mapnik/issues/1873 - [True, True, long], + [True, True, int], [None, False, None], - [2147483648, True, long], - [922337203685477580, True, long] + [2147483648, True, int], + [922337203685477580, True, int] ] @@ -334,26 +316,25 @@ def test_expressions_for_thruthyness(): for eq in truthyness: f = mapnik.Feature(context, 0) f["prop"] = eq[0] - eq_(f["prop"], eq[0]) + assert f["prop"] == eq[0] if eq[0] is None: - eq_(f["prop"] is None, True) + assert f["prop"] is None else: - eq_(isinstance(f['prop'], eq[2]), True, - '%s is not an instance of %s' % (f['prop'], eq[2])) + assert isinstance(f['prop'], eq[2]), '%s is not an instance of %s' % (f['prop'], eq[2]) expr = mapnik.Expression("[prop]") - eq_(expr.to_bool(f), eq[1]) + assert expr.to_bool(f) == eq[1] expr = mapnik.Expression("not [prop]") - eq_(expr.to_bool(f), not eq[1]) + assert not expr.to_bool(f) == eq[1] expr = mapnik.Expression("! [prop]") - eq_(expr.to_bool(f), not eq[1]) + assert not expr.to_bool(f) == eq[1] # also test if feature does not have property at all f2 = mapnik.Feature(context, 1) # no property existing will return value_null since # https://github.com/mapnik/mapnik/commit/562fada9d0f680f59b2d9f396c95320a0d753479#include/mapnik/feature.hpp - eq_(f2["prop"] is None, True) + assert f2["prop"] is None expr = mapnik.Expression("[prop]") - eq_(expr.evaluate(f2), None) - eq_(expr.to_bool(f2), False) + assert expr.evaluate(f2) == None + assert expr.to_bool(f2) == False # https://github.com/mapnik/mapnik/issues/1859 @@ -364,93 +345,86 @@ def test_if_null_and_empty_string_are_equal(): f["empty"] = u"" f["null"] = None # ensure base assumptions are good - eq_(mapnik.Expression("[empty] = ''").to_bool(f), True) - eq_(mapnik.Expression("[null] = null").to_bool(f), True) - eq_(mapnik.Expression("[empty] != ''").to_bool(f), False) - eq_(mapnik.Expression("[null] != null").to_bool(f), False) + assert mapnik.Expression("[empty] = ''").to_bool(f) + assert mapnik.Expression("[null] = null").to_bool(f) + assert not mapnik.Expression("[empty] != ''").to_bool(f) + assert not mapnik.Expression("[null] != null").to_bool(f) # now test expected behavior - eq_(mapnik.Expression("[null] = ''").to_bool(f), False) - eq_(mapnik.Expression("[empty] = null").to_bool(f), False) - eq_(mapnik.Expression("[empty] != null").to_bool(f), True) + assert not mapnik.Expression("[null] = ''").to_bool(f) + assert not mapnik.Expression("[empty] = null").to_bool(f) + assert mapnik.Expression("[empty] != null").to_bool(f) # this one is the back compatibility shim - eq_(mapnik.Expression("[null] != ''").to_bool(f), False) + assert not mapnik.Expression("[null] != ''").to_bool(f) def test_filtering_nulls_and_empty_strings(): context = mapnik.Context() f = mapnik.Feature(context, 0) f["prop"] = u"hello" - eq_(f["prop"], u"hello") - eq_(mapnik.Expression("[prop]").to_bool(f), True) - eq_(mapnik.Expression("! [prop]").to_bool(f), False) - eq_(mapnik.Expression("[prop] != null").to_bool(f), True) - eq_(mapnik.Expression("[prop] != ''").to_bool(f), True) - eq_(mapnik.Expression("[prop] != null and [prop] != ''").to_bool(f), True) - eq_(mapnik.Expression("[prop] != null or [prop] != ''").to_bool(f), True) + assert f["prop"] == u"hello" + assert mapnik.Expression("[prop]").to_bool(f) + assert not mapnik.Expression("! [prop]").to_bool(f) + assert mapnik.Expression("[prop] != null").to_bool(f) + assert mapnik.Expression("[prop] != ''").to_bool(f) + assert mapnik.Expression("[prop] != null and [prop] != ''").to_bool(f) + assert mapnik.Expression("[prop] != null or [prop] != ''").to_bool(f) f["prop2"] = u"" - eq_(f["prop2"], u"") - eq_(mapnik.Expression("[prop2]").to_bool(f), False) - eq_(mapnik.Expression("! [prop2]").to_bool(f), True) - eq_(mapnik.Expression("[prop2] != null").to_bool(f), True) - eq_(mapnik.Expression("[prop2] != ''").to_bool(f), False) - eq_(mapnik.Expression("[prop2] = ''").to_bool(f), True) - eq_(mapnik.Expression("[prop2] != null or [prop2] != ''").to_bool(f), True) - eq_(mapnik.Expression( - "[prop2] != null and [prop2] != ''").to_bool(f), False) + assert f["prop2"] == u"" + assert not mapnik.Expression("[prop2]").to_bool(f) + assert mapnik.Expression("! [prop2]").to_bool(f) + assert mapnik.Expression("[prop2] != null").to_bool(f) + assert not mapnik.Expression("[prop2] != ''").to_bool(f) + assert mapnik.Expression("[prop2] = ''").to_bool(f) + assert mapnik.Expression("[prop2] != null or [prop2] != ''").to_bool(f) + assert not mapnik.Expression("[prop2] != null and [prop2] != ''").to_bool(f) f["prop3"] = None - eq_(f["prop3"], None) - eq_(mapnik.Expression("[prop3]").to_bool(f), False) - eq_(mapnik.Expression("! [prop3]").to_bool(f), True) - eq_(mapnik.Expression("[prop3] != null").to_bool(f), False) - eq_(mapnik.Expression("[prop3] = null").to_bool(f), True) + assert f["prop3"] == None + assert not mapnik.Expression("[prop3]").to_bool(f) + assert mapnik.Expression("! [prop3]").to_bool(f) + assert not mapnik.Expression("[prop3] != null").to_bool(f) + assert mapnik.Expression("[prop3] = null").to_bool(f) # https://github.com/mapnik/mapnik/issues/1859 - #eq_(mapnik.Expression("[prop3] != ''").to_bool(f),True) - eq_(mapnik.Expression("[prop3] != ''").to_bool(f), False) + #assert mapnik.Expression("[prop3] != ''").to_bool(f) == True + assert not mapnik.Expression("[prop3] != ''").to_bool(f) - eq_(mapnik.Expression("[prop3] = ''").to_bool(f), False) + assert not mapnik.Expression("[prop3] = ''").to_bool(f) # https://github.com/mapnik/mapnik/issues/1859 - #eq_(mapnik.Expression("[prop3] != null or [prop3] != ''").to_bool(f),True) - eq_(mapnik.Expression( - "[prop3] != null or [prop3] != ''").to_bool(f), False) + #assert mapnik.Expression("[prop3] != null or [prop3] != ''").to_bool(f) == True + assert not mapnik.Expression("[prop3] != null or [prop3] != ''").to_bool(f) - eq_(mapnik.Expression( - "[prop3] != null and [prop3] != ''").to_bool(f), False) + assert not mapnik.Expression("[prop3] != null and [prop3] != ''").to_bool(f) # attr not existing should behave the same as prop3 - eq_(mapnik.Expression("[prop4]").to_bool(f), False) - eq_(mapnik.Expression("! [prop4]").to_bool(f), True) - eq_(mapnik.Expression("[prop4] != null").to_bool(f), False) - eq_(mapnik.Expression("[prop4] = null").to_bool(f), True) + assert not mapnik.Expression("[prop4]").to_bool(f) + assert mapnik.Expression("! [prop4]").to_bool(f) + assert not mapnik.Expression("[prop4] != null").to_bool(f) + assert mapnik.Expression("[prop4] = null").to_bool(f) # https://github.com/mapnik/mapnik/issues/1859 - ##eq_(mapnik.Expression("[prop4] != ''").to_bool(f),True) - eq_(mapnik.Expression("[prop4] != ''").to_bool(f), False) + ##assert mapnik.Expression("[prop4] != ''").to_bool(f) == True + assert not mapnik.Expression("[prop4] != ''").to_bool(f) - eq_(mapnik.Expression("[prop4] = ''").to_bool(f), False) + assert not mapnik.Expression("[prop4] = ''").to_bool(f) # https://github.com/mapnik/mapnik/issues/1859 - ##eq_(mapnik.Expression("[prop4] != null or [prop4] != ''").to_bool(f),True) - eq_(mapnik.Expression( - "[prop4] != null or [prop4] != ''").to_bool(f), False) + ##assert mapnik.Expression("[prop4] != null or [prop4] != ''").to_bool(f) == True + assert not mapnik.Expression("[prop4] != null or [prop4] != ''").to_bool(f) - eq_(mapnik.Expression( - "[prop4] != null and [prop4] != ''").to_bool(f), False) + assert not mapnik.Expression("[prop4] != null and [prop4] != ''").to_bool(f) f["prop5"] = False - eq_(f["prop5"], False) - eq_(mapnik.Expression("[prop5]").to_bool(f), False) - eq_(mapnik.Expression("! [prop5]").to_bool(f), True) - eq_(mapnik.Expression("[prop5] != null").to_bool(f), True) - eq_(mapnik.Expression("[prop5] = null").to_bool(f), False) - eq_(mapnik.Expression("[prop5] != ''").to_bool(f), True) - eq_(mapnik.Expression("[prop5] = ''").to_bool(f), False) - eq_(mapnik.Expression("[prop5] != null or [prop5] != ''").to_bool(f), True) - eq_(mapnik.Expression( - "[prop5] != null and [prop5] != ''").to_bool(f), True) + assert f["prop5"] == False + assert not mapnik.Expression("[prop5]").to_bool(f) + assert mapnik.Expression("! [prop5]").to_bool(f) + assert mapnik.Expression("[prop5] != null").to_bool(f) + assert not mapnik.Expression("[prop5] = null").to_bool(f) + assert mapnik.Expression("[prop5] != ''").to_bool(f) + assert not mapnik.Expression("[prop5] = ''").to_bool(f) + assert mapnik.Expression("[prop5] != null or [prop5] != ''").to_bool(f) + assert mapnik.Expression("[prop5] != null and [prop5] != ''").to_bool(f) # note, we need to do [prop5] != 0 here instead of false due to this bug: # https://github.com/mapnik/mapnik/issues/1873 - eq_(mapnik.Expression( - "[prop5] != null and [prop5] != '' and [prop5] != 0").to_bool(f), False) + assert not mapnik.Expression("[prop5] != null and [prop5] != '' and [prop5] != 0").to_bool(f) # https://github.com/mapnik/mapnik/issues/1872 @@ -459,12 +433,12 @@ def test_falseyness_comparision(): context = mapnik.Context() f = mapnik.Feature(context, 0) f["prop"] = 0 - eq_(mapnik.Expression("[prop]").to_bool(f), False) - eq_(mapnik.Expression("[prop] = false").to_bool(f), True) - eq_(mapnik.Expression("not [prop] != false").to_bool(f), True) - eq_(mapnik.Expression("not [prop] = true").to_bool(f), True) - eq_(mapnik.Expression("[prop] = true").to_bool(f), False) - eq_(mapnik.Expression("[prop] != true").to_bool(f), True) + assert not mapnik.Expression("[prop]").to_bool(f) + assert mapnik.Expression("[prop] = false").to_bool(f) + assert mapnik.Expression("not [prop] != false").to_bool(f) + assert mapnik.Expression("not [prop] = true").to_bool(f) + assert not mapnik.Expression("[prop] = true").to_bool(f) + assert mapnik.Expression("[prop] != true").to_bool(f) # https://github.com/mapnik/mapnik/issues/1806, fixed by # https://github.com/mapnik/mapnik/issues/1872 @@ -474,12 +448,12 @@ def test_truthyness_comparision(): context = mapnik.Context() f = mapnik.Feature(context, 0) f["prop"] = 1 - eq_(mapnik.Expression("[prop]").to_bool(f), True) - eq_(mapnik.Expression("[prop] = false").to_bool(f), False) - eq_(mapnik.Expression("not [prop] != false").to_bool(f), False) - eq_(mapnik.Expression("not [prop] = true").to_bool(f), False) - eq_(mapnik.Expression("[prop] = true").to_bool(f), True) - eq_(mapnik.Expression("[prop] != true").to_bool(f), False) + assert mapnik.Expression("[prop]").to_bool(f) == True + assert mapnik.Expression("[prop] = false").to_bool(f) == False + assert mapnik.Expression("not [prop] != false").to_bool(f) == False + assert mapnik.Expression("not [prop] = true").to_bool(f) == False + assert mapnik.Expression("[prop] = true").to_bool(f) == True + assert mapnik.Expression("[prop] != true").to_bool(f) == False def test_division_by_zero(): @@ -490,13 +464,9 @@ def test_division_by_zero(): f = mapnik.Feature(c, 0) f['a'] = 1 f['b'] = 0 - eq_(expr.evaluate(f), None) + assert expr.evaluate(f) == None -@raises(RuntimeError) def test_invalid_syntax1(): - mapnik.Expression('abs()') - - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + with pytest.raises(RuntimeError): + mapnik.Expression('abs()') diff --git a/test/python_tests/fontset_test.py b/test/python_tests/fontset_test.py index 0baed51fd..3fb01dce0 100644 --- a/test/python_tests/fontset_test.py +++ b/test/python_tests/fontset_test.py @@ -1,47 +1,28 @@ -#!/usr/bin/env python - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_loading_fontset_from_map(): m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/fontset.xml', True) + mapnik.load_map(m, './test/data/good_maps/fontset.xml', True) fs = m.find_fontset('book-fonts') - eq_(len(fs.names), 2) - eq_(list(fs.names), ['DejaVu Sans Book', 'DejaVu Sans Oblique']) + assert len(fs.names) == 2 + assert list(fs.names) == ['DejaVu Sans Book', 'DejaVu Sans Oblique'] # def test_loading_fontset_from_python(): # m = mapnik.Map(256,256) # fset = mapnik.FontSet('foo') # fset.add_face_name('Comic Sans') # fset.add_face_name('Papyrus') -# eq_(fset.name,'foo') +# assert fset.name == 'foo' # fset.name = 'my-set' -# eq_(fset.name,'my-set') +# assert fset.name == 'my-set' # m.append_fontset('my-set', fset) # sty = mapnik.Style() # rule = mapnik.Rule() # tsym = mapnik.TextSymbolizer() -# eq_(tsym.fontset,None) +# assert tsym.fontset == None # tsym.fontset = fset # rule.symbols.append(tsym) # sty.rules.append(rule) # m.append_style('Style',sty) # serialized_map = mapnik.save_map_to_string(m) -# eq_('fontset-name="my-set"' in serialized_map,True) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) +# assert 'fontset-name="my-set"' in serialized_map == True diff --git a/test/python_tests/geojson_plugin_test.py b/test/python_tests/geojson_plugin_test.py index dfd40acac..557ef242a 100644 --- a/test/python_tests/geojson_plugin_test.py +++ b/test/python_tests/geojson_plugin_test.py @@ -1,104 +1,90 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - -from nose.tools import assert_almost_equal, eq_ - import mapnik - -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) +import pytest if 'geojson' in mapnik.DatasourceCache.plugin_names(): def test_geojson_init(): ds = mapnik.Datasource( type='geojson', - file='../data/json/escaped.geojson') + file='./test/data/json/escaped.geojson') e = ds.envelope() - assert_almost_equal(e.minx, -81.705583, places=7) - assert_almost_equal(e.miny, 41.480573, places=6) - assert_almost_equal(e.maxx, -81.705583, places=5) - assert_almost_equal(e.maxy, 41.480573, places=3) + assert e.minx == pytest.approx(-81.705583, abs=1e-7) + assert e.miny == pytest.approx(41.480573, abs=1e-6) + assert e.maxx == pytest.approx(-81.705583, abs=1e-5) + assert e.maxy == pytest.approx(41.480573, abs=1e-3) def test_geojson_properties(): ds = mapnik.Datasource( type='geojson', - file='../data/json/escaped.geojson') + file='./test/data/json/escaped.geojson') f = list(ds.features_at_point(ds.envelope().center()))[0] - eq_(len(ds.fields()), 11) + assert len(ds.fields()) == 11 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point - eq_(f['name'], u'Test') - eq_(f['int'], 1) - eq_(f['description'], u'Test: \u005C') - eq_(f['spaces'], u'this has spaces') - eq_(f['double'], 1.1) - eq_(f['boolean'], True) - eq_(f['NOM_FR'], u'Qu\xe9bec') - eq_(f['NOM_FR'], u'Québec') + assert f['name'] == u'Test' + assert f['int'] == 1 + assert f['description'] == u'Test: \u005C' + assert f['spaces'] == u'this has spaces' + assert f['double'] == 1.1 + assert f['boolean'] == True + assert f['NOM_FR'] == u'Qu\xe9bec' + assert f['NOM_FR'] == u'Québec' ds = mapnik.Datasource( type='geojson', - file='../data/json/escaped.geojson') + file='./test/data/json/escaped.geojson') f = list(ds.all_features())[0] - eq_(len(ds.fields()), 11) + assert len(ds.fields()) == 11 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point - eq_(f['name'], u'Test') - eq_(f['int'], 1) - eq_(f['description'], u'Test: \u005C') - eq_(f['spaces'], u'this has spaces') - eq_(f['double'], 1.1) - eq_(f['boolean'], True) - eq_(f['NOM_FR'], u'Qu\xe9bec') - eq_(f['NOM_FR'], u'Québec') + assert f['name'] == u'Test' + assert f['int'] == 1 + assert f['description'] == u'Test: \u005C' + assert f['spaces'] == u'this has spaces' + assert f['double'] == 1.1 + assert f['boolean'] == True + assert f['NOM_FR'] == u'Qu\xe9bec' + assert f['NOM_FR'] == u'Québec' def test_large_geojson_properties(): ds = mapnik.Datasource( type='geojson', - file='../data/json/escaped.geojson', + file='./test/data/json/escaped.geojson', cache_features=False) f = list(ds.features_at_point(ds.envelope().center()))[0] - eq_(len(ds.fields()), 11) + assert len(ds.fields()) == 11 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point - eq_(f['name'], u'Test') - eq_(f['int'], 1) - eq_(f['description'], u'Test: \u005C') - eq_(f['spaces'], u'this has spaces') - eq_(f['double'], 1.1) - eq_(f['boolean'], True) - eq_(f['NOM_FR'], u'Qu\xe9bec') - eq_(f['NOM_FR'], u'Québec') + assert f['name'] == u'Test' + assert f['int'] == 1 + assert f['description'] == u'Test: \u005C' + assert f['spaces'] == u'this has spaces' + assert f['double'] == 1.1 + assert f['boolean'] == True + assert f['NOM_FR'] == u'Qu\xe9bec' + assert f['NOM_FR'] == u'Québec' ds = mapnik.Datasource( type='geojson', - file='../data/json/escaped.geojson') + file='./test/data/json/escaped.geojson') f = list(ds.all_features())[0] - eq_(len(ds.fields()), 11) + assert len(ds.fields()) == 11 desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point - eq_(f['name'], u'Test') - eq_(f['int'], 1) - eq_(f['description'], u'Test: \u005C') - eq_(f['spaces'], u'this has spaces') - eq_(f['double'], 1.1) - eq_(f['boolean'], True) - eq_(f['NOM_FR'], u'Qu\xe9bec') - eq_(f['NOM_FR'], u'Québec') + assert f['name'] == u'Test' + assert f['int'] == 1 + assert f['description'] == u'Test: \u005C' + assert f['spaces'] == u'this has spaces' + assert f['double'] == 1.1 + assert f['boolean'] == True + assert f['NOM_FR'] == u'Qu\xe9bec' + assert f['NOM_FR'] == u'Québec' def test_geojson_from_in_memory_string(): # will silently fail since it is a geometry and needs to be a featurecollection. @@ -107,21 +93,21 @@ def test_geojson_from_in_memory_string(): ds = mapnik.Datasource( type='geojson', inline='{ "type":"FeatureCollection", "features": [ { "type":"Feature", "properties":{"name":"test"}, "geometry": { "type":"LineString","coordinates":[[0,0],[10,10]] } } ]}') - eq_(len(ds.fields()), 1) + assert len(ds.fields()) == 1 f = list(ds.all_features())[0] desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.LineString) - eq_(f['name'], u'test') + assert desc['geometry_type'] == mapnik.DataGeometryType.LineString + assert f['name'] == u'test' # @raises(RuntimeError) def test_that_nonexistant_query_field_throws(**kwargs): ds = mapnik.Datasource( type='geojson', - file='../data/json/escaped.geojson') - eq_(len(ds.fields()), 11) + file='./test/data/json/escaped.geojson') + assert len(ds.fields()) == 11 # TODO - this sorting is messed up - #eq_(ds.fields(),['name', 'int', 'double', 'description', 'boolean', 'NOM_FR']) - #eq_(ds.field_types(),['str', 'int', 'float', 'str', 'bool', 'str']) + #assert ds.fields(),['name', 'int', 'double', 'description', 'boolean' == 'NOM_FR'] + #assert ds.field_types(),['str', 'int', 'float', 'str', 'bool' == 'str'] # TODO - should geojson plugin throw like others? # query = mapnik.Query(ds.envelope()) # for fld in ds.fields(): @@ -133,13 +119,9 @@ def test_that_nonexistant_query_field_throws(**kwargs): def test_parsing_feature_collection_with_top_level_properties(): ds = mapnik.Datasource( type='geojson', - file='../data/json/feature_collection_level_properties.json') + file='./test/data/json/feature_collection_level_properties.json') f = list(ds.all_features())[0] desc = ds.describe() - eq_(desc['geometry_type'], mapnik.DataGeometryType.Point) - eq_(f['feat_name'], u'feat_value') - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert desc['geometry_type'] == mapnik.DataGeometryType.Point + assert f['feat_name'] == u'feat_value' diff --git a/test/python_tests/geometry_io_test.py b/test/python_tests/geometry_io_test.py index f1bac0b4e..f24b90198 100644 --- a/test/python_tests/geometry_io_test.py +++ b/test/python_tests/geometry_io_test.py @@ -1,25 +1,12 @@ -# encoding: utf8 - -import os from binascii import unhexlify - -from nose.tools import eq_, assert_raises - import mapnik - -from .utilities import execution_path, run_all - +import pytest try: import json except ImportError: import simplejson as json -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - wkts = [ [mapnik.GeometryType.Point, "POINT(30 10)", @@ -183,20 +170,20 @@ def setup(): def test_path_geo_interface(): geom = mapnik.Geometry.from_wkt('POINT(0 0)') - eq_(geom.__geo_interface__, {u'type': u'Point', u'coordinates': [0, 0]}) + assert geom.__geo_interface__, {u'type': u'Point', u'coordinates': [0 == 0]} def test_valid_wkb_parsing(): count = 0 for wkb in empty_wkbs: geom = mapnik.Geometry.from_wkb(unhexlify(wkb[2])) - eq_(geom.is_empty(), True) - eq_(geom.type(), wkb[0]) + assert geom.is_empty() == True + assert geom.type() == wkb[0] for wkb in wkts: geom = mapnik.Geometry.from_wkb(unhexlify(wkb[2])) - eq_(geom.is_empty(), False) - eq_(geom.type(), wkb[0]) + assert geom.is_empty() == False + assert geom.type() == wkb[0] def test_wkb_parsing_error(): @@ -205,7 +192,7 @@ def test_wkb_parsing_error(): try: geom = mapnik.Geometry.from_wkb(unhexlify(wkb)) # should not get here - eq_(True, False) + assert True == False except: pass assert True @@ -218,8 +205,8 @@ def test_empty_wkb_parsing(): count = 0 for wkb in partially_empty_wkb: geom = mapnik.Geometry.from_wkb(unhexlify(wkb[2])) - eq_(geom.type(), wkb[0]) - eq_(geom.is_empty(), False) + assert geom.type() == wkb[0] + assert geom.is_empty() == False def test_geojson_parsing(): @@ -228,14 +215,14 @@ def test_geojson_parsing(): for j in geojson: count += 1 geometries.append(mapnik.Geometry.from_geojson(j[1])) - eq_(count, len(geometries)) + assert count == len(geometries) def test_geojson_parsing_reversed(): for idx, j in enumerate(geojson_reversed): g1 = mapnik.Geometry.from_geojson(j) g2 = mapnik.Geometry.from_geojson(geojson[idx][1]) - eq_(g1.to_geojson(), g2.to_geojson()) + assert g1.to_geojson() == g2.to_geojson() # http://geojson.org/geojson-spec.html#positions @@ -243,44 +230,44 @@ def test_geojson_parsing_reversed(): def test_geojson_point_positions(): input_json = '{"type":"Point","coordinates":[30,10]}' geom = mapnik.Geometry.from_geojson(input_json) - eq_(geom.to_geojson(), input_json) + assert geom.to_geojson() == input_json # should ignore all but the first two geom = mapnik.Geometry.from_geojson( '{"type":"Point","coordinates":[30,10,50,50,50,50]}') - eq_(geom.to_geojson(), input_json) + assert geom.to_geojson() == input_json def test_geojson_point_positions2(): input_json = '{"type":"LineString","coordinates":[[30,10],[10,30],[40,40]]}' geom = mapnik.Geometry.from_geojson(input_json) - eq_(geom.to_geojson(), input_json) + assert geom.to_geojson() == input_json # should ignore all but the first two geom = mapnik.Geometry.from_geojson( '{"type":"LineString","coordinates":[[30.0,10.0,0,0,0],[10.0,30.0,0,0,0],[40.0,40.0,0,0,0]]}') - eq_(geom.to_geojson(), input_json) + assert geom.to_geojson() == input_json def compare_wkb_from_wkt(wkt, type): geom = mapnik.Geometry.from_wkt(wkt) - eq_(geom.type(), type) + assert geom.type() == type def compare_wkt_to_geojson(idx, wkt, num=None): geom = mapnik.Geometry.from_wkt(wkt) # ensure both have same result gj = geom.to_geojson() - eq_(len(gj) > 1, True) + assert len(gj) > 1 == True a = json.loads(gj) e = json.loads(geojson[idx][1]) - eq_(a, e) + assert a == e def test_wkt_simple(): for wkt in wkts: try: geom = mapnik.Geometry.from_wkt(wkt[1]) - eq_(geom.type(), wkt[0]) + assert geom.type() == wkt[0] except RuntimeError as e: raise RuntimeError('%s %s' % (e, wkt)) @@ -308,7 +295,7 @@ def test_wkt_rounding(): # if precision is set to 15 still fails due to very subtle rounding issues wkt = "POLYGON((7.904185 54.180426,7.89918 54.178168,7.897715 54.182318,7.893565 54.183111,7.890391 54.187567,7.885874 54.19068,7.879893 54.193915,7.894541 54.194647,7.900645 54.19068,7.904185 54.180426))" geom = mapnik.Geometry.from_wkt(wkt) - eq_(geom.type(), mapnik.GeometryType.Polygon) + assert geom.type() == mapnik.GeometryType.Polygon def test_wkt_collection_flattening(): @@ -316,7 +303,7 @@ def test_wkt_collection_flattening(): # currently fails as the MULTIPOLYGON inside will be returned as multiple polygons - not a huge deal - should we worry? #wkt = "GEOMETRYCOLLECTION(POLYGON((1 1,2 1,2 2,1 2,1 1)),MULTIPOLYGON(((40 40,20 45,45 30,40 40)),((20 35,45 20,30 5,10 10,10 30,20 35),(30 20,20 25,20 15,30 20))),LINESTRING(2 3,3 4))" geom = mapnik.Geometry.from_wkt(wkt) - eq_(geom.type(), mapnik.GeometryType.GeometryCollection) + assert geom.type() == mapnik.GeometryType.GeometryCollection def test_creating_feature_from_geojson(): @@ -327,8 +314,8 @@ def test_creating_feature_from_geojson(): } ctx = mapnik.Context() feat = mapnik.Feature.from_geojson(json.dumps(json_feat), ctx) - eq_(feat.id(), 1) - eq_(feat['name'], u'value') + assert feat.id() == 1 + assert feat['name'] == u'value' def test_handling_valid_geojson_empty_geometries(): @@ -336,13 +323,10 @@ def test_handling_valid_geojson_empty_geometries(): geom = mapnik.Geometry.from_geojson(json) out_json = geom.to_geojson() # check round trip - eq_(json.replace(" ",""), out_json) + assert json.replace(" ","") == out_json def test_handling_invalid_geojson_empty_geometries(): - for json in invalid_empty_geometries: - assert_raises(RuntimeError, mapnik.Geometry.from_geojson, json) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + with pytest.raises(RuntimeError): + for json in invalid_empty_geometries: + mapnik.Geometry.from_geojson(json) diff --git a/test/python_tests/grayscale_test.py b/test/python_tests/grayscale_test.py index fad019223..96e33bd5e 100644 --- a/test/python_tests/grayscale_test.py +++ b/test/python_tests/grayscale_test.py @@ -1,16 +1,8 @@ -from nose.tools import eq_ - import mapnik -from .utilities import run_all - - def test_grayscale_conversion(): im = mapnik.Image(2, 2) im.fill(mapnik.Color('white')) im.set_grayscale_to_alpha() pixel = im.get_pixel(0, 0) - eq_((pixel >> 24) & 0xff, 255) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert (pixel >> 24) & 0xff == 255 diff --git a/test/python_tests/image_encoding_speed_test.py b/test/python_tests/image_encoding_speed_test.py index 4d990465d..cafa842b9 100644 --- a/test/python_tests/image_encoding_speed_test.py +++ b/test/python_tests/image_encoding_speed_test.py @@ -1,19 +1,6 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os from timeit import Timer, time - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - combinations = ['png', 'png8', 'png8:m=o', @@ -121,9 +108,3 @@ def aerial_24(): print( 'min: %sms | avg: %sms | total: %sms | len: %s <-- %s' % (min_, avg, elapsed, size, name)) - - -if __name__ == "__main__": - setup() - do_encoding() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) From f61bfebcb0211707999b03227be4c3f55cfcdc8c Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Tue, 31 Jan 2023 10:46:46 +0000 Subject: [PATCH 06/37] convert even more unit tests to use pytest [WIP] --- test/python_tests/image_test.py | 320 +++++++-------- test/python_tests/image_tiff_test.py | 371 +++++++----------- test/python_tests/introspection_test.py | 43 +- .../json_feature_properties_test.py | 25 +- test/python_tests/layer_buffer_size_test.py | 34 +- test/python_tests/layer_modification_test.py | 47 +-- test/python_tests/layer_test.py | 42 +- test/python_tests/load_map_test.py | 30 +- test/python_tests/map_query_test.py | 95 ++--- 9 files changed, 390 insertions(+), 617 deletions(-) diff --git a/test/python_tests/image_test.py b/test/python_tests/image_test.py index f25ff39c8..ba758b5af 100644 --- a/test/python_tests/image_test.py +++ b/test/python_tests/image_test.py @@ -1,48 +1,30 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os -import sys - -from nose.tools import assert_almost_equal, eq_, raises - import mapnik +import pytest -from .utilities import READ_FLAGS, execution_path, get_unique_colors, run_all - -PYTHON3 = sys.version_info[0] == 3 -if PYTHON3: - buffer = memoryview - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - +from .utilities import READ_FLAGS, get_unique_colors def test_type(): im = mapnik.Image(256, 256) - eq_(im.get_type(), mapnik.ImageType.rgba8) + assert im.get_type() == mapnik.ImageType.rgba8 im = mapnik.Image(256, 256, mapnik.ImageType.gray8) - eq_(im.get_type(), mapnik.ImageType.gray8) + assert im.get_type() == mapnik.ImageType.gray8 def test_image_premultiply(): im = mapnik.Image(256, 256) - eq_(im.premultiplied(), False) + assert im.premultiplied() == False # Premultiply should return true that it worked - eq_(im.premultiply(), True) - eq_(im.premultiplied(), True) + assert im.premultiply() == True + assert im.premultiplied() == True # Premultipling again should return false as nothing should happen - eq_(im.premultiply(), False) - eq_(im.premultiplied(), True) + assert im.premultiply() == False + assert im.premultiplied() == True # Demultiply should return true that it worked - eq_(im.demultiply(), True) - eq_(im.premultiplied(), False) + assert im.demultiply() == True + assert im.premultiplied() == False # Demultiply again should not work and return false as it did nothing - eq_(im.demultiply(), False) - eq_(im.premultiplied(), False) + assert im.demultiply() == False + assert im.premultiplied() == False def test_image_premultiply_values(): @@ -50,18 +32,18 @@ def test_image_premultiply_values(): im.fill(mapnik.Color(16, 33, 255, 128)) im.premultiply() c = im.get_pixel(0, 0, True) - eq_(c.r, 8) - eq_(c.g, 17) - eq_(c.b, 128) - eq_(c.a, 128) + assert c.r == 8 + assert c.g == 17 + assert c.b == 128 + assert c.a == 128 im.demultiply() # Do to the nature of this operation the result will not be exactly the # same c = im.get_pixel(0, 0, True) - eq_(c.r, 15) - eq_(c.g, 33) - eq_(c.b, 255) - eq_(c.a, 128) + assert c.r == 15 + assert c.g == 33 + assert c.b == 255 + assert c.a == 128 def test_apply_opacity(): @@ -69,32 +51,32 @@ def test_apply_opacity(): im.fill(mapnik.Color(128, 128, 128, 128)) im.apply_opacity(0.75) c = im.get_pixel(0, 0, True) - eq_(c.r, 128) - eq_(c.g, 128) - eq_(c.b, 128) - eq_(c.a, 96) + assert c.r == 128 + assert c.g == 128 + assert c.b == 128 + assert c.a == 96 def test_background(): im = mapnik.Image(256, 256) - eq_(im.premultiplied(), False) + assert im.premultiplied() == False im.fill(mapnik.Color(32, 64, 125, 128)) - eq_(im.premultiplied(), False) + assert im.premultiplied() == False c = im.get_pixel(0, 0, True) - eq_(c.get_premultiplied(), False) - eq_(c.r, 32) - eq_(c.g, 64) - eq_(c.b, 125) - eq_(c.a, 128) + assert c.get_premultiplied() == False + assert c.r == 32 + assert c.g == 64 + assert c.b == 125 + assert c.a == 128 # Now again with a premultiplied alpha im.fill(mapnik.Color(32, 64, 125, 128, True)) - eq_(im.premultiplied(), True) + assert im.premultiplied() == True c = im.get_pixel(0, 0, True) - eq_(c.get_premultiplied(), True) - eq_(c.r, 32) - eq_(c.g, 64) - eq_(c.b, 125) - eq_(c.a, 128) + assert c.get_premultiplied() == True + assert c.r == 32 + assert c.g == 64 + assert c.b == 125 + assert c.a == 128 def test_set_and_get_pixel(): @@ -106,27 +88,27 @@ def test_set_and_get_pixel(): im.set_pixel(1, 1, c0_pre) # No differences for non premultiplied pixels c1_int = mapnik.Color(im.get_pixel(0, 0)) - eq_(c0.r, c1_int.r) - eq_(c0.g, c1_int.g) - eq_(c0.b, c1_int.b) - eq_(c0.a, c1_int.a) + assert c0.r == c1_int.r + assert c0.g == c1_int.g + assert c0.b == c1_int.b + assert c0.a == c1_int.a c1 = im.get_pixel(0, 0, True) - eq_(c0.r, c1.r) - eq_(c0.g, c1.g) - eq_(c0.b, c1.b) - eq_(c0.a, c1.a) + assert c0.r == c1.r + assert c0.g == c1.g + assert c0.b == c1.b + assert c0.a == c1.a # The premultiplied Color should be demultiplied before being applied. c0_pre.demultiply() c1_int = mapnik.Color(im.get_pixel(1, 1)) - eq_(c0_pre.r, c1_int.r) - eq_(c0_pre.g, c1_int.g) - eq_(c0_pre.b, c1_int.b) - eq_(c0_pre.a, c1_int.a) + assert c0_pre.r == c1_int.r + assert c0_pre.g == c1_int.g + assert c0_pre.b == c1_int.b + assert c0_pre.a == c1_int.a c1 = im.get_pixel(1, 1, True) - eq_(c0_pre.r, c1.r) - eq_(c0_pre.g, c1.g) - eq_(c0_pre.b, c1.b) - eq_(c0_pre.a, c1.a) + assert c0_pre.r == c1.r + assert c0_pre.g == c1.g + assert c0_pre.b == c1.b + assert c0_pre.a == c1.a # Now create a new image that is premultiplied im = mapnik.Image(256, 256, mapnik.ImageType.rgba8, True, True) @@ -138,26 +120,26 @@ def test_set_and_get_pixel(): # premultiply c0 c0.premultiply() c1_int = mapnik.Color(im.get_pixel(0, 0)) - eq_(c0.r, c1_int.r) - eq_(c0.g, c1_int.g) - eq_(c0.b, c1_int.b) - eq_(c0.a, c1_int.a) + assert c0.r == c1_int.r + assert c0.g == c1_int.g + assert c0.b == c1_int.b + assert c0.a == c1_int.a c1 = im.get_pixel(0, 0, True) - eq_(c0.r, c1.r) - eq_(c0.g, c1.g) - eq_(c0.b, c1.b) - eq_(c0.a, c1.a) + assert c0.r == c1.r + assert c0.g == c1.g + assert c0.b == c1.b + assert c0.a == c1.a # The premultiplied Color should be the same though c1_int = mapnik.Color(im.get_pixel(1, 1)) - eq_(c0_pre.r, c1_int.r) - eq_(c0_pre.g, c1_int.g) - eq_(c0_pre.b, c1_int.b) - eq_(c0_pre.a, c1_int.a) + assert c0_pre.r == c1_int.r + assert c0_pre.g == c1_int.g + assert c0_pre.b == c1_int.b + assert c0_pre.a == c1_int.a c1 = im.get_pixel(1, 1, True) - eq_(c0_pre.r, c1.r) - eq_(c0_pre.g, c1.g) - eq_(c0_pre.b, c1.b) - eq_(c0_pre.a, c1.a) + assert c0_pre.r == c1.r + assert c0_pre.g == c1.g + assert c0_pre.b == c1.b + assert c0_pre.a == c1.a def test_pixel_gray8(): @@ -165,9 +147,9 @@ def test_pixel_gray8(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), 0) + assert im.get_pixel(0, 0) == 0 def test_pixel_gray8s(): @@ -175,9 +157,9 @@ def test_pixel_gray8s(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), -v) + assert im.get_pixel(0, 0) == -v def test_pixel_gray16(): @@ -185,9 +167,9 @@ def test_pixel_gray16(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), 0) + assert im.get_pixel(0, 0) == 0 def test_pixel_gray16s(): @@ -195,9 +177,9 @@ def test_pixel_gray16s(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), -v) + assert im.get_pixel(0, 0) == -v def test_pixel_gray32(): @@ -205,9 +187,9 @@ def test_pixel_gray32(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), 0) + assert im.get_pixel(0, 0) == 0 def test_pixel_gray32s(): @@ -215,9 +197,9 @@ def test_pixel_gray32s(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), -v) + assert im.get_pixel(0, 0) == -v def test_pixel_gray64(): @@ -225,9 +207,9 @@ def test_pixel_gray64(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), 0) + assert im.get_pixel(0, 0) == 0 def test_pixel_gray64s(): @@ -235,9 +217,9 @@ def test_pixel_gray64s(): val_list = range(20) for v in val_list: im.set_pixel(0, 0, v) - eq_(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == v im.set_pixel(0, 0, -v) - eq_(im.get_pixel(0, 0), -v) + assert im.get_pixel(0, 0) == -v def test_pixel_floats(): @@ -245,9 +227,9 @@ def test_pixel_floats(): val_list = [0.9, 0.99, 0.999, 0.9999, 0.99999, 1, 1.0001, 1.001, 1.01, 1.1] for v in val_list: im.set_pixel(0, 0, v) - assert_almost_equal(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == pytest.approx(v) im.set_pixel(0, 0, -v) - assert_almost_equal(im.get_pixel(0, 0), -v) + assert im.get_pixel(0, 0) == pytest.approx(-v) def test_pixel_doubles(): @@ -255,80 +237,80 @@ def test_pixel_doubles(): val_list = [0.9, 0.99, 0.999, 0.9999, 0.99999, 1, 1.0001, 1.001, 1.01, 1.1] for v in val_list: im.set_pixel(0, 0, v) - assert_almost_equal(im.get_pixel(0, 0), v) + assert im.get_pixel(0, 0) == pytest.approx(v) im.set_pixel(0, 0, -v) - assert_almost_equal(im.get_pixel(0, 0), -v) + assert im.get_pixel(0, 0) == pytest.approx(-v) def test_pixel_overflow(): im = mapnik.Image(4, 4, mapnik.ImageType.gray8) im.set_pixel(0, 0, 256) - eq_(im.get_pixel(0, 0), 255) + assert im.get_pixel(0, 0) == 255 def test_pixel_underflow(): im = mapnik.Image(4, 4, mapnik.ImageType.gray8) im.set_pixel(0, 0, -1) - eq_(im.get_pixel(0, 0), 0) + assert im.get_pixel(0, 0) == 0 im = mapnik.Image(4, 4, mapnik.ImageType.gray16) im.set_pixel(0, 0, -1) - eq_(im.get_pixel(0, 0), 0) + assert im.get_pixel(0, 0) == 0 -@raises(IndexError) def test_set_pixel_out_of_range_1(): - im = mapnik.Image(4, 4) - c = mapnik.Color('blue') - im.set_pixel(5, 5, c) + with pytest.raises(IndexError): + im = mapnik.Image(4, 4) + c = mapnik.Color('blue') + im.set_pixel(5, 5, c) -@raises(OverflowError) def test_set_pixel_out_of_range_2(): - im = mapnik.Image(4, 4) - c = mapnik.Color('blue') - im.set_pixel(-1, 1, c) + with pytest.raises(OverflowError): + im = mapnik.Image(4, 4) + c = mapnik.Color('blue') + im.set_pixel(-1, 1, c) -@raises(IndexError) def test_get_pixel_out_of_range_1(): - im = mapnik.Image(4, 4) - c = im.get_pixel(5, 5) + with pytest.raises(IndexError): + im = mapnik.Image(4, 4) + c = im.get_pixel(5, 5) -@raises(OverflowError) def test_get_pixel_out_of_range_2(): - im = mapnik.Image(4, 4) - c = im.get_pixel(-1, 1) + with pytest.raises(OverflowError): + im = mapnik.Image(4, 4) + c = im.get_pixel(-1, 1) -@raises(IndexError) def test_get_pixel_color_out_of_range_1(): - im = mapnik.Image(4, 4) - c = im.get_pixel(5, 5, True) + with pytest.raises(IndexError): + im = mapnik.Image(4, 4) + c = im.get_pixel(5, 5, True) -@raises(OverflowError) def test_get_pixel_color_out_of_range_2(): - im = mapnik.Image(4, 4) - c = im.get_pixel(-1, 1, True) + with pytest.raises(OverflowError): + im = mapnik.Image(4, 4) + c = im.get_pixel(-1, 1, True) def test_set_color_to_alpha(): im = mapnik.Image(256, 256) im.fill(mapnik.Color('rgba(12,12,12,255)')) - eq_(get_unique_colors(im), ['rgba(12,12,12,255)']) + assert get_unique_colors(im), ['rgba(12,12,12 == 255)'] im.set_color_to_alpha(mapnik.Color('rgba(12,12,12,0)')) - eq_(get_unique_colors(im), ['rgba(0,0,0,0)']) + assert get_unique_colors(im), ['rgba(0,0,0 == 0)'] -@raises(RuntimeError) def test_negative_image_dimensions(): - # TODO - this may have regressed in - # https://github.com/mapnik/mapnik/commit/4f3521ac24b61fc8ae8fd344a16dc3a5fdf15af7 - im = mapnik.Image(-40, 40) - # should not get here - eq_(im.width(), 0) - eq_(im.height(), 0) + with pytest.raises(RuntimeError): + # TODO - this may have regressed in + # https://github.com/mapnik/mapnik/commit/4f3521ac24b61fc8ae8fd344a16dc3a5fdf15af7 + im = mapnik.Image(-40, 40) + # should not get here + assert im.width() == 0 + assert im.height() == 0 def test_jpeg_round_trip(): @@ -339,14 +321,14 @@ def test_jpeg_round_trip(): im2 = mapnik.Image.open(filepath) with open(filepath, READ_FLAGS) as f: im3 = mapnik.Image.fromstring(f.read()) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(im.width(), im3.width()) - eq_(im.height(), im3.height()) - eq_(len(im.tostring()), len(im2.tostring())) - eq_(len(im.tostring('jpeg')), len(im2.tostring('jpeg'))) - eq_(len(im.tostring()), len(im3.tostring())) - eq_(len(im.tostring('jpeg')), len(im3.tostring('jpeg'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert im.width() == im3.width() + assert im.height() == im3.height() + assert len(im.tostring()) == len(im2.tostring()) + assert len(im.tostring('jpeg')) == len(im2.tostring('jpeg')) + assert len(im.tostring()) == len(im3.tostring()) + assert len(im.tostring('jpeg')) == len(im3.tostring('jpeg')) def test_png_round_trip(): @@ -357,35 +339,31 @@ def test_png_round_trip(): im2 = mapnik.Image.open(filepath) with open(filepath, READ_FLAGS) as f: im3 = mapnik.Image.fromstring(f.read()) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(im.width(), im3.width()) - eq_(im.height(), im3.height()) - eq_(len(im.tostring()), len(im2.tostring())) - eq_(len(im.tostring('png')), len(im2.tostring('png'))) - eq_(len(im.tostring('png8')), len(im2.tostring('png8'))) - eq_(len(im.tostring()), len(im3.tostring())) - eq_(len(im.tostring('png')), len(im3.tostring('png'))) - eq_(len(im.tostring('png8')), len(im3.tostring('png8'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert im.width() == im3.width() + assert im.height() == im3.height() + assert len(im.tostring()) == len(im2.tostring()) + assert len(im.tostring('png')) == len(im2.tostring('png')) + assert len(im.tostring('png8')) == len(im2.tostring('png8')) + assert len(im.tostring()) == len(im3.tostring()) + assert len(im.tostring('png')) == len(im3.tostring('png')) + assert len(im.tostring('png8')) == len(im3.tostring('png8')) def test_image_open_from_string(): - filepath = '../data/images/dummy.png' + filepath = './test/data/images/dummy.png' im1 = mapnik.Image.open(filepath) with open(filepath, READ_FLAGS) as f: im2 = mapnik.Image.fromstring(f.read()) - eq_(im1.width(), im2.width()) + assert im1.width() == im2.width() length = len(im1.tostring()) - eq_(length, len(im2.tostring())) - eq_(len(mapnik.Image.fromstring(im1.tostring('png')).tostring()), length) - eq_(len(mapnik.Image.fromstring(im1.tostring('jpeg')).tostring()), length) - eq_(len(mapnik.Image.frombuffer(buffer(im1.tostring('png'))).tostring()), length) - eq_(len(mapnik.Image.frombuffer(buffer(im1.tostring('jpeg'))).tostring()), length) + assert length == len(im2.tostring()) + assert len(mapnik.Image.fromstring(im1.tostring('png')).tostring()) == length + assert len(mapnik.Image.fromstring(im1.tostring('jpeg')).tostring()) == length + assert len(mapnik.Image.frombuffer(memoryview(im1.tostring('png'))).tostring()) == length + assert len(mapnik.Image.frombuffer(memoryview(im1.tostring('jpeg'))).tostring()) == length # TODO - https://github.com/mapnik/mapnik/issues/1831 - eq_(len(mapnik.Image.fromstring(im1.tostring('tiff')).tostring()), length) - eq_(len(mapnik.Image.frombuffer(buffer(im1.tostring('tiff'))).tostring()), length) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert len(mapnik.Image.fromstring(im1.tostring('tiff')).tostring()) == length + assert len(mapnik.Image.frombuffer(memoryview(im1.tostring('tiff'))).tostring()) == length diff --git a/test/python_tests/image_tiff_test.py b/test/python_tests/image_tiff_test.py index b1915c111..c5fcc395f 100644 --- a/test/python_tests/image_tiff_test.py +++ b/test/python_tests/image_tiff_test.py @@ -1,26 +1,11 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - import hashlib -import os - -from nose.tools import assert_not_equal, eq_ - import mapnik -from .utilities import READ_FLAGS, execution_path, run_all - +from .utilities import READ_FLAGS def hashstr(var): return hashlib.md5(var).hexdigest() - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_tiff_round_trip_scanline(): filepath = '/tmp/mapnik-tiff-io-scanline.tiff' im = mapnik.Image(255, 267) @@ -30,26 +15,21 @@ def test_tiff_round_trip_scanline(): im2 = mapnik.Image.open(filepath) with open(filepath, READ_FLAGS) as f: im3 = mapnik.Image.fromstring(f.read()) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(im.width(), im3.width()) - eq_(im.height(), im3.height()) - eq_(hashstr(im.tostring()), org_str) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert im.width() == im3.width() + assert im.height() == im3.height() + assert hashstr(im.tostring()) == org_str # This won't be the same the first time around because the im is not # premultiplied and im2 is - assert_not_equal(hashstr(im.tostring()), hashstr(im2.tostring())) - assert_not_equal( - hashstr( - im.tostring('tiff:method=scanline')), hashstr( - im2.tostring('tiff:method=scanline'))) + assert not hashstr(im.tostring()) == hashstr(im2.tostring()) + assert not hashstr(im.tostring('tiff:method=scanline')) == hashstr(im2.tostring('tiff:method=scanline')) # Now premultiply im.premultiply() - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=scanline')), - hashstr(im2.tostring('tiff:method=scanline'))) - eq_(hashstr(im2.tostring()), hashstr(im3.tostring())) - eq_(hashstr(im2.tostring('tiff:method=scanline')), - hashstr(im3.tostring('tiff:method=scanline'))) + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=scanline')) == hashstr(im2.tostring('tiff:method=scanline')) + assert hashstr(im2.tostring()) == hashstr(im3.tostring()) + assert hashstr(im2.tostring('tiff:method=scanline')) == hashstr(im3.tostring('tiff:method=scanline')) def test_tiff_round_trip_stripped(): @@ -62,27 +42,22 @@ def test_tiff_round_trip_stripped(): im2.save('/tmp/mapnik-tiff-io-stripped2.tiff', 'tiff:method=stripped') with open(filepath, READ_FLAGS) as f: im3 = mapnik.Image.fromstring(f.read()) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(im.width(), im3.width()) - eq_(im.height(), im3.height()) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert im.width() == im3.width() + assert im.height() == im3.height() # Because one will end up with UNASSOC alpha tag which internally the TIFF reader will premultiply, the first to string will not be the same due to the # difference in tags. - assert_not_equal(hashstr(im.tostring()), hashstr(im2.tostring())) - assert_not_equal( - hashstr( - im.tostring('tiff:method=stripped')), hashstr( - im2.tostring('tiff:method=stripped'))) + assert not hashstr(im.tostring()) == hashstr(im2.tostring()) + assert not hashstr(im.tostring('tiff:method=stripped')) == hashstr(im2.tostring('tiff:method=stripped')) # Now if we premultiply they will be exactly the same im.premultiply() - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=stripped')), - hashstr(im2.tostring('tiff:method=stripped'))) - eq_(hashstr(im2.tostring()), hashstr(im3.tostring())) + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=stripped')) == hashstr(im2.tostring('tiff:method=stripped')) + assert hashstr(im2.tostring()) == hashstr(im3.tostring()) # Both of these started out premultiplied, so this round trip should be # exactly the same! - eq_(hashstr(im2.tostring('tiff:method=stripped')), - hashstr(im3.tostring('tiff:method=stripped'))) + assert hashstr(im2.tostring('tiff:method=stripped')) == hashstr(im3.tostring('tiff:method=stripped')) def test_tiff_round_trip_rows_stripped(): @@ -91,42 +66,38 @@ def test_tiff_round_trip_rows_stripped(): im = mapnik.Image(255, 267) im.fill(mapnik.Color('rgba(12,255,128,.5)')) c = im.get_pixel(0, 0, True) - eq_(c.r, 12) - eq_(c.g, 255) - eq_(c.b, 128) - eq_(c.a, 128) - eq_(c.get_premultiplied(), False) + assert c.r == 12 + assert c.g == 255 + assert c.b == 128 + assert c.a == 128 + assert c.get_premultiplied() == False im.save(filepath, 'tiff:method=stripped:rows_per_strip=8') im2 = mapnik.Image.open(filepath) c2 = im2.get_pixel(0, 0, True) - eq_(c2.r, 6) - eq_(c2.g, 128) - eq_(c2.b, 64) - eq_(c2.a, 128) - eq_(c2.get_premultiplied(), True) + assert c2.r == 6 + assert c2.g == 128 + assert c2.b == 64 + assert c2.a == 128 + assert c2.get_premultiplied() == True im2.save(filepath2, 'tiff:method=stripped:rows_per_strip=8') with open(filepath, READ_FLAGS) as f: im3 = mapnik.Image.fromstring(f.read()) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(im.width(), im3.width()) - eq_(im.height(), im3.height()) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert im.width() == im3.width() + assert im.height() == im3.height() # Because one will end up with UNASSOC alpha tag which internally the TIFF reader will premultiply, the first to string will not be the same due to the # difference in tags. - assert_not_equal(hashstr(im.tostring()), hashstr(im2.tostring())) - assert_not_equal( - hashstr( - im.tostring('tiff:method=stripped:rows_per_strip=8')), hashstr( - im2.tostring('tiff:method=stripped:rows_per_strip=8'))) + assert not hashstr(im.tostring()) == hashstr(im2.tostring()) + assert not hashstr(im.tostring('tiff:method=stripped:rows_per_strip=8')) == hashstr( + im2.tostring('tiff:method=stripped:rows_per_strip=8')) # Now premultiply the first image and they will be the same! im.premultiply() - eq_(hashstr(im.tostring('tiff:method=stripped:rows_per_strip=8')), - hashstr(im2.tostring('tiff:method=stripped:rows_per_strip=8'))) - eq_(hashstr(im2.tostring()), hashstr(im3.tostring())) + assert hashstr(im.tostring('tiff:method=stripped:rows_per_strip=8')) == hashstr(im2.tostring('tiff:method=stripped:rows_per_strip=8')) + assert hashstr(im2.tostring()) == hashstr(im3.tostring()) # Both of these started out premultiplied, so this round trip should be # exactly the same! - eq_(hashstr(im2.tostring('tiff:method=stripped:rows_per_strip=8')), - hashstr(im3.tostring('tiff:method=stripped:rows_per_strip=8'))) + assert hashstr(im2.tostring('tiff:method=stripped:rows_per_strip=8')) == hashstr(im3.tostring('tiff:method=stripped:rows_per_strip=8')) def test_tiff_round_trip_buffered_tiled(): @@ -136,44 +107,40 @@ def test_tiff_round_trip_buffered_tiled(): im = mapnik.Image(255, 267) im.fill(mapnik.Color('rgba(33,255,128,.5)')) c = im.get_pixel(0, 0, True) - eq_(c.r, 33) - eq_(c.g, 255) - eq_(c.b, 128) - eq_(c.a, 128) - eq_(c.get_premultiplied(), False) + assert c.r == 33 + assert c.g == 255 + assert c.b == 128 + assert c.a == 128 + assert not c.get_premultiplied() im.save(filepath, 'tiff:method=tiled:tile_width=32:tile_height=32') im2 = mapnik.Image.open(filepath) c2 = im2.get_pixel(0, 0, True) - eq_(c2.r, 17) - eq_(c2.g, 128) - eq_(c2.b, 64) - eq_(c2.a, 128) - eq_(c2.get_premultiplied(), True) + assert c2.r == 17 + assert c2.g == 128 + assert c2.b == 64 + assert c2.a == 128 + assert c2.get_premultiplied() with open(filepath, READ_FLAGS) as f: im3 = mapnik.Image.fromstring(f.read()) im2.save(filepath2, 'tiff:method=tiled:tile_width=32:tile_height=32') im3.save(filepath3, 'tiff:method=tiled:tile_width=32:tile_height=32') - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(im.width(), im3.width()) - eq_(im.height(), im3.height()) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert im.width() == im3.width() + assert im.height() == im3.height() # Because one will end up with UNASSOC alpha tag which internally the TIFF reader will premultiply, the first to string will not be the same due to the # difference in tags. - assert_not_equal(hashstr(im.tostring()), hashstr(im2.tostring())) - assert_not_equal( - hashstr( - im.tostring('tiff:method=tiled:tile_width=32:tile_height=32')), hashstr( - im2.tostring('tiff:method=tiled:tile_width=32:tile_height=32'))) + assert not hashstr(im.tostring()) == hashstr(im2.tostring()) + assert not hashstr(im.tostring('tiff:method=tiled:tile_width=32:tile_height=32')) == hashstr( + im2.tostring('tiff:method=tiled:tile_width=32:tile_height=32')) # Now premultiply the first image and they should be the same im.premultiply() - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=tiled:tile_width=32:tile_height=32')), - hashstr(im2.tostring('tiff:method=tiled:tile_width=32:tile_height=32'))) - eq_(hashstr(im2.tostring()), hashstr(im3.tostring())) + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=tiled:tile_width=32:tile_height=32')) == hashstr(im2.tostring('tiff:method=tiled:tile_width=32:tile_height=32')) + assert hashstr(im2.tostring()) == hashstr(im3.tostring()) # Both of these started out premultiplied, so this round trip should be # exactly the same! - eq_(hashstr(im2.tostring('tiff:method=tiled:tile_width=32:tile_height=32')), - hashstr(im3.tostring('tiff:method=tiled:tile_width=32:tile_height=32'))) + assert hashstr(im2.tostring('tiff:method=tiled:tile_width=32:tile_height=32')) == hashstr(im3.tostring('tiff:method=tiled:tile_width=32:tile_height=32')) def test_tiff_round_trip_tiled(): @@ -184,235 +151,199 @@ def test_tiff_round_trip_tiled(): im2 = mapnik.Image.open(filepath) with open(filepath, READ_FLAGS) as f: im3 = mapnik.Image.fromstring(f.read()) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(im.width(), im3.width()) - eq_(im.height(), im3.height()) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert im.width() == im3.width() + assert im.height() == im3.height() # Because one will end up with UNASSOC alpha tag which internally the TIFF reader will premultiply, the first to string will not be the same due to the # difference in tags. - assert_not_equal(hashstr(im.tostring()), hashstr(im2.tostring())) - assert_not_equal( - hashstr( - im.tostring('tiff:method=tiled')), hashstr( - im2.tostring('tiff:method=tiled'))) + assert not hashstr(im.tostring()) == hashstr(im2.tostring()) + assert not hashstr(im.tostring('tiff:method=tiled')) == hashstr(im2.tostring('tiff:method=tiled')) # Now premultiply the first image and they will be exactly the same. im.premultiply() - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=tiled')), - hashstr(im2.tostring('tiff:method=tiled'))) - eq_(hashstr(im2.tostring()), hashstr(im3.tostring())) + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=tiled')) == hashstr(im2.tostring('tiff:method=tiled')) + assert hashstr(im2.tostring()) == hashstr(im3.tostring()) # Both of these started out premultiplied, so this round trip should be # exactly the same! - eq_(hashstr(im2.tostring('tiff:method=tiled')), - hashstr(im3.tostring('tiff:method=tiled'))) + assert hashstr(im2.tostring('tiff:method=tiled')) == hashstr(im3.tostring('tiff:method=tiled')) def test_tiff_rgb8_compare(): - filepath1 = '../data/tiff/ndvi_256x256_rgb8_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_rgb8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgb8.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff')), hashstr(im2.tostring('tiff'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff')) == hashstr(im2.tostring('tiff')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")) def test_tiff_rgba8_compare_scanline(): - filepath1 = '../data/tiff/ndvi_256x256_rgba8_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_rgba8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgba8-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=scanline')), - hashstr(im2.tostring('tiff:method=scanline'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=scanline')) == hashstr(im2.tostring('tiff:method=scanline')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")) def test_tiff_rgba8_compare_stripped(): - filepath1 = '../data/tiff/ndvi_256x256_rgba8_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_rgba8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgba8-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=stripped')), - hashstr(im2.tostring('tiff:method=stripped'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=stripped')) == hashstr(im2.tostring('tiff:method=stripped')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")) def test_tiff_rgba8_compare_tiled(): - filepath1 = '../data/tiff/ndvi_256x256_rgba8_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_rgba8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgba8-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=tiled')), - hashstr(im2.tostring('tiff:method=tiled'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=tiled')) == hashstr(im2.tostring('tiff:method=tiled')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.rgba8).tostring("tiff")) def test_tiff_gray8_compare_scanline(): - filepath1 = '../data/tiff/ndvi_256x256_gray8_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray8_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray8-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=scanline')), - hashstr(im2.tostring('tiff:method=scanline'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=scanline')) == hashstr(im2.tostring('tiff:method=scanline')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.gray8).tostring("tiff")), True) - + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray8).tostring("tiff")) def test_tiff_gray8_compare_stripped(): - filepath1 = '../data/tiff/ndvi_256x256_gray8_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray8_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray8-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=stripped')), - hashstr(im2.tostring('tiff:method=stripped'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=stripped')) == hashstr(im2.tostring('tiff:method=stripped')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.gray8).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray8).tostring("tiff")) def test_tiff_gray8_compare_tiled(): - filepath1 = '../data/tiff/ndvi_256x256_gray8_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray8_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray8-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=tiled')), - hashstr(im2.tostring('tiff:method=tiled'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=tiled')) == hashstr(im2.tostring('tiff:method=tiled')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.gray8).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray8).tostring("tiff")) def test_tiff_gray16_compare_scanline(): - filepath1 = '../data/tiff/ndvi_256x256_gray16_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray16_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray16-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=scanline')), - hashstr(im2.tostring('tiff:method=scanline'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=scanline')) == hashstr(im2.tostring('tiff:method=scanline')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.gray16).tostring("tiff")), True) - + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray16).tostring("tiff")) def test_tiff_gray16_compare_stripped(): - filepath1 = '../data/tiff/ndvi_256x256_gray16_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray16_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray16-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=stripped')), - hashstr(im2.tostring('tiff:method=stripped'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=stripped')) == hashstr(im2.tostring('tiff:method=stripped')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.gray16).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray16).tostring("tiff")) def test_tiff_gray16_compare_tiled(): - filepath1 = '../data/tiff/ndvi_256x256_gray16_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray16_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray16-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=tiled')), - hashstr(im2.tostring('tiff:method=tiled'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=tiled')) == hashstr(im2.tostring('tiff:method=tiled')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image( - im.width(), im.height(), mapnik.ImageType.gray16).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray16).tostring("tiff")) def test_tiff_gray32f_compare_scanline(): - filepath1 = '../data/tiff/ndvi_256x256_gray32f_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray32f_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray32f-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=scanline')), - hashstr(im2.tostring('tiff:method=scanline'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=scanline')) == hashstr(im2.tostring('tiff:method=scanline')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), - im.height(), mapnik.ImageType.gray32f).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray32f).tostring("tiff")) def test_tiff_gray32f_compare_stripped(): - filepath1 = '../data/tiff/ndvi_256x256_gray32f_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray32f_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray32f-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=stripped')), - hashstr(im2.tostring('tiff:method=stripped'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=stripped')) == hashstr(im2.tostring('tiff:method=stripped')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), - im.height(), mapnik.ImageType.gray32f).tostring("tiff")), True) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray32f).tostring("tiff")) def test_tiff_gray32f_compare_tiled(): - filepath1 = '../data/tiff/ndvi_256x256_gray32f_striped.tif' + filepath1 = './test/data/tiff/ndvi_256x256_gray32f_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray32f-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') im2 = mapnik.Image.open(filepath2) - eq_(im.width(), im2.width()) - eq_(im.height(), im2.height()) - eq_(hashstr(im.tostring()), hashstr(im2.tostring())) - eq_(hashstr(im.tostring('tiff:method=tiled')), - hashstr(im2.tostring('tiff:method=tiled'))) + assert im.width() == im2.width() + assert im.height() == im2.height() + assert hashstr(im.tostring()) == hashstr(im2.tostring()) + assert hashstr(im.tostring('tiff:method=tiled')) == hashstr(im2.tostring('tiff:method=tiled')) # should not be a blank image - eq_(hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), - im.height(), mapnik.ImageType.gray32f).tostring("tiff")), True) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray32f).tostring("tiff")) diff --git a/test/python_tests/introspection_test.py b/test/python_tests/introspection_test.py index 0c1e39dd2..215be7d3f 100644 --- a/test/python_tests/introspection_test.py +++ b/test/python_tests/introspection_test.py @@ -1,36 +1,21 @@ -#!/usr/bin/env python - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_introspect_symbolizers(): # create a symbolizer p = mapnik.PointSymbolizer() - p.file = "../data/images/dummy.png" + p.file = "./test/data/images/dummy.png" p.allow_overlap = True p.opacity = 0.5 - eq_(p.allow_overlap, True) - eq_(p.opacity, 0.5) - eq_(p.filename, '../data/images/dummy.png') + assert p.allow_overlap == True + assert p.opacity == 0.5 + assert p.filename == './test/data/images/dummy.png' # make sure the defaults # are what we think they are - eq_(p.allow_overlap, True) - eq_(p.opacity, 0.5) - eq_(p.filename, '../data/images/dummy.png') + assert p.allow_overlap == True + assert p.opacity == 0.5 + assert p.filename == './test/data/images/dummy.png' # contruct objects to hold it r = mapnik.Rule() @@ -46,20 +31,16 @@ def test_introspect_symbolizers(): s2 = m.find_style('s') rules = s2.rules - eq_(len(rules), 1) + assert len(rules) == 1 r2 = rules[0] syms = r2.symbols - eq_(len(syms), 1) + assert len(syms) == 1 # TODO here, we can do... sym = syms[0] p2 = sym.extract() assert isinstance(p2, mapnik.PointSymbolizer) - eq_(p2.allow_overlap, True) - eq_(p2.opacity, 0.5) - eq_(p2.filename, '../data/images/dummy.png') - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert p2.allow_overlap == True + assert p2.opacity == 0.5 + assert p2.filename == './test/data/images/dummy.png' diff --git a/test/python_tests/json_feature_properties_test.py b/test/python_tests/json_feature_properties_test.py index 41557455c..10ae884d8 100644 --- a/test/python_tests/json_feature_properties_test.py +++ b/test/python_tests/json_feature_properties_test.py @@ -1,11 +1,4 @@ -# encoding: utf8 - -from nose.tools import eq_ - import mapnik - -from .utilities import run_all - try: import json except ImportError: @@ -83,30 +76,20 @@ ctx = mapnik.Context() ctx.push('name') - def test_char_escaping(): for char in chars: feat = mapnik.Feature(ctx, 1) expected = char['test'] feat["name"] = expected - eq_(feat["name"], expected) + assert feat["name"] == expected # confirm the python json module # is working as we would expect pyjson2 = json.loads(char['json']) - eq_(pyjson2['properties']['name'], expected) + assert pyjson2['properties']['name'] == expected # confirm our behavior is the same as python json module # for the original string geojson_feat_string = feat.to_geojson() - eq_( - geojson_feat_string, - char['json'], - "Mapnik's json escaping is not to spec: actual(%s) and expected(%s) for %s" % - (geojson_feat_string, - char['json'], - char['name'])) + assert geojson_feat_string == char['json'], "Mapnik's json escaping is not to spec: actual(%s) and expected(%s) for %s" % (geojson_feat_string, char['json'], char['name']) # and the round tripped string pyjson = json.loads(geojson_feat_string) - eq_(pyjson['properties']['name'], expected) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert pyjson['properties']['name'] == expected diff --git a/test/python_tests/layer_buffer_size_test.py b/test/python_tests/layer_buffer_size_test.py index 30417a367..093fe7221 100644 --- a/test/python_tests/layer_buffer_size_test.py +++ b/test/python_tests/layer_buffer_size_test.py @@ -1,18 +1,5 @@ -# coding=utf8 -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - if 'sqlite' in mapnik.DatasourceCache.plugin_names(): # the negative buffer on the layer should @@ -20,23 +7,16 @@ def setup(): # only one point to be rendered in the map def test_layer_buffer_size_1(): m = mapnik.Map(512, 512) - eq_(m.buffer_size, 0) - mapnik.load_map(m, '../data/good_maps/layer_buffer_size_reduction.xml') - eq_(m.buffer_size, 256) - eq_(m.layers[0].buffer_size, -150) + assert m.buffer_size == 0 + mapnik.load_map(m, './test/data/good_maps/layer_buffer_size_reduction.xml') + assert m.buffer_size == 256 + assert m.layers[0].buffer_size == -150 m.zoom_all() im = mapnik.Image(m.width, m.height) mapnik.render(m, im) actual = '/tmp/mapnik-layer-buffer-size.png' - expected = 'images/support/mapnik-layer-buffer-size.png' + expected = './test/python_tests/images/support/mapnik-layer-buffer-size.png' im.save(actual, "png32") expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'tests/python_tests/' + expected)) - - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im.tostring('png32') == expected_im.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual, + 'tests/python_tests/' + expected) diff --git a/test/python_tests/layer_modification_test.py b/test/python_tests/layer_modification_test.py index 373a57618..37ac73ed1 100644 --- a/test/python_tests/layer_modification_test.py +++ b/test/python_tests/layer_modification_test.py @@ -1,20 +1,5 @@ -#!/usr/bin/env python - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_adding_datasource_to_layer(): map_string = ''' @@ -25,7 +10,7 @@ def test_adding_datasource_to_layer(): @@ -39,9 +24,9 @@ def test_adding_datasource_to_layer(): mapnik.load_map_from_string(m, map_string) # validate it loaded fine - eq_(m.layers[0].styles[0], 'world_borders_style') - eq_(m.layers[0].styles[1], 'point_style') - eq_(len(m.layers), 1) + assert m.layers[0].styles[0] == 'world_borders_style' + assert m.layers[0].styles[1] == 'point_style' + assert len(m.layers) == 1 # also assign a variable reference to that layer # below we will test that this variable references @@ -49,35 +34,29 @@ def test_adding_datasource_to_layer(): lyr = m.layers[0] # ensure that there was no datasource for the layer... - eq_(m.layers[0].datasource, None) - eq_(lyr.datasource, None) + assert m.layers[0].datasource == None + assert lyr.datasource == None # also note that since the srs was black it defaulted to wgs84 - eq_(m.layers[0].srs, - 'epsg:4326') - eq_(lyr.srs, 'epsg:4326') + assert m.layers[0].srs == 'epsg:4326' + assert lyr.srs == 'epsg:4326' # now add a datasource one... - ds = mapnik.Shapefile(file='../data/shp/world_merc.shp') + ds = mapnik.Shapefile(file='./test/data/shp/world_merc.shp') m.layers[0].datasource = ds # now ensure it is attached - eq_(m.layers[0].datasource.describe()['name'], "shape") - eq_(lyr.datasource.describe()['name'], "shape") + assert m.layers[0].datasource.describe()['name'] == "shape" + assert lyr.datasource.describe()['name'] == "shape" # and since we have now added a shapefile in spherical mercator, adjust # the projection lyr.srs = '+proj=merc +lon_0=0 +lat_ts=0 +x_0=0 +y_0=0 +ellps=WGS84 +datum=WGS84 +units=m +no_defs' # test that assignment - eq_(m.layers[ - 0].srs, '+proj=merc +lon_0=0 +lat_ts=0 +x_0=0 +y_0=0 +ellps=WGS84 +datum=WGS84 +units=m +no_defs') - eq_(lyr.srs, '+proj=merc +lon_0=0 +lat_ts=0 +x_0=0 +y_0=0 +ellps=WGS84 +datum=WGS84 +units=m +no_defs') + assert m.layers[0].srs == '+proj=merc +lon_0=0 +lat_ts=0 +x_0=0 +y_0=0 +ellps=WGS84 +datum=WGS84 +units=m +no_defs' + assert lyr.srs == '+proj=merc +lon_0=0 +lat_ts=0 +x_0=0 +y_0=0 +ellps=WGS84 +datum=WGS84 +units=m +no_defs' except RuntimeError as e: # only test datasources that we have installed if not 'Could not create datasource' in str(e): raise RuntimeError(e) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) diff --git a/test/python_tests/layer_test.py b/test/python_tests/layer_test.py index f096e2589..e8652bbc0 100644 --- a/test/python_tests/layer_test.py +++ b/test/python_tests/layer_test.py @@ -1,33 +1,21 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -from nose.tools import eq_ - import mapnik -from .utilities import run_all - - # Map initialization - def test_layer_init(): l = mapnik.Layer('test') - eq_(l.name, 'test') - eq_(l.srs, 'epsg:4326') - eq_(l.envelope(), mapnik.Box2d()) - eq_(l.clear_label_cache, False) - eq_(l.cache_features, False) - eq_(l.visible(1), True) - eq_(l.active, True) - eq_(l.datasource, None) - eq_(l.queryable, False) - eq_(l.minimum_scale_denominator, 0.0) - eq_(l.maximum_scale_denominator > 1e+6, True) - eq_(l.group_by, "") - eq_(l.maximum_extent, None) - eq_(l.buffer_size, None) - eq_(len(l.styles), 0) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert l.name == 'test' + assert l.srs == 'epsg:4326' + assert l.envelope() == mapnik.Box2d() + assert not l.clear_label_cache + assert not l.cache_features + assert l.visible(1) + assert l.active + assert l.datasource == None + assert not l.queryable + assert l.minimum_scale_denominator == 0.0 + assert l.maximum_scale_denominator > 1e+6 + assert l.group_by == "" + assert l.maximum_extent == None + assert l.buffer_size == None + assert len(l.styles) == 0 diff --git a/test/python_tests/load_map_test.py b/test/python_tests/load_map_test.py index ea0b5ccd8..85d23f8ac 100644 --- a/test/python_tests/load_map_test.py +++ b/test/python_tests/load_map_test.py @@ -1,31 +1,11 @@ -#!/usr/bin/env python - import glob -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - default_logging_severity = mapnik.logger.get_severity() - -def setup(): - # make the tests silent to suppress unsupported params from harfbuzz tests - # TODO: remove this after harfbuzz branch merges - mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def teardown(): mapnik.logger.set_severity(default_logging_severity) - def test_broken_files(): default_logging_severity = mapnik.logger.get_severity() mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) @@ -44,7 +24,7 @@ def test_broken_files(): filename) except RuntimeError: pass - eq_(len(failures), 0, '\n' + '\n'.join(failures)) + assert len(failures) == 0, '\n' + '\n'.join(failures) mapnik.logger.set_severity(default_logging_severity) @@ -75,7 +55,7 @@ def test_can_parse_xml_with_deprecated_properties(): failures.append( 'Failed to load valid map %s (%s)' % (filename, e)) - eq_(len(failures), 0, '\n' + '\n'.join(failures)) + assert len(failures) == 0, '\n' + '\n'.join(failures) mapnik.logger.set_severity(default_logging_severity) @@ -100,8 +80,4 @@ def test_good_files(): failures.append( 'Failed to load valid map %s (%s)' % (filename, e)) - eq_(len(failures), 0, '\n' + '\n'.join(failures)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert len(failures) == 0, '\n' + '\n'.join(failures) diff --git a/test/python_tests/map_query_test.py b/test/python_tests/map_query_test.py index ab8335e14..268f7fbf3 100644 --- a/test/python_tests/map_query_test.py +++ b/test/python_tests/map_query_test.py @@ -1,63 +1,44 @@ -#!/usr/bin/env python - -import os - -from nose.tools import assert_almost_equal, eq_, raises - import mapnik - -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) +import pytest # map has no layers - - -@raises(IndexError) def test_map_query_throw1(): - m = mapnik.Map(256, 256) - m.zoom_to_box(mapnik.Box2d(-1, -1, 0, 0)) - m.query_point(0, 0, 0) + with pytest.raises(IndexError): + m = mapnik.Map(256, 256) + m.zoom_to_box(mapnik.Box2d(-1, -1, 0, 0)) + m.query_point(0, 0, 0) # only positive indexes - - -@raises(IndexError) def test_map_query_throw2(): - m = mapnik.Map(256, 256) - m.query_point(-1, 0, 0) + with pytest.raises(IndexError): + m = mapnik.Map(256, 256) + m.query_point(-1, 0, 0) # map has never been zoomed (nodata) - - -@raises(RuntimeError) def test_map_query_throw3(): - m = mapnik.Map(256, 256) - m.query_point(0, 0, 0) + with pytest.raises(RuntimeError): + m = mapnik.Map(256, 256) + m.query_point(0, 0, 0) if 'shape' in mapnik.DatasourceCache.plugin_names(): # map has never been zoomed (even with data) - @raises(RuntimeError) def test_map_query_throw4(): - m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') - m.query_point(0, 0, 0) + with pytest.raises(RuntimeError): + m = mapnik.Map(256, 256) + mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') + m.query_point(0, 0, 0) # invalid coords in general (do not intersect) - @raises(RuntimeError) def test_map_query_throw5(): - m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') - m.zoom_all() - m.query_point(0, 9999999999999999, 9999999999999999) + with pytest.raises(RuntimeError): + m = mapnik.Map(256, 256) + mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') + m.zoom_all() + m.query_point(0, 9999999999999999, 9999999999999999) def test_map_query_works1(): m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/wgs842merc_reprojection.xml') + mapnik.load_map(m, './test/data/good_maps/wgs842merc_reprojection.xml') merc_bounds = mapnik.Box2d(-20037508.34, - 20037508.34, 20037508.34, 20037508.34) m.maximum_extent = merc_bounds @@ -65,11 +46,11 @@ def test_map_query_works1(): # somewhere in kansas fs = m.query_point(0, -11012435.5376, 4599674.6134) feat = fs.next() - eq_(feat.attributes['NAME_FORMA'], u'United States of America') + assert feat.attributes['NAME_FORMA'] == u'United States of America' def test_map_query_works2(): m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/merc2wgs84_reprojection.xml') + mapnik.load_map(m, './test/data/good_maps/merc2wgs84_reprojection.xml') wgs84_bounds = mapnik.Box2d(-179.999999975, - 85.0511287776, 179.999999975, 85.0511287776) m.maximum_extent = wgs84_bounds @@ -78,28 +59,28 @@ def test_map_query_works2(): # mapnik.render_to_file(m,'works2.png') # validate that aspect_fix_mode modified the bbox reasonably e = m.envelope() - assert_almost_equal(e.minx, -179.999999975, places=7) - assert_almost_equal(e.miny, -167.951396161, places=7) - assert_almost_equal(e.maxx, 179.999999975, places=7) - assert_almost_equal(e.maxy, 192.048603789, places=7) + assert e.minx == pytest.approx(-179.999999975, abs=1e-7) + assert e.miny == pytest.approx(-167.951396161, abs=1e-7) + assert e.maxx == pytest.approx(179.999999975, abs=1e-7) + assert e.maxy == pytest.approx(192.048603789, abs=1e-7) fs = m.query_point(0, -98.9264, 38.1432) # somewhere in kansas feat = fs.next() - eq_(feat.attributes['NAME'], u'United States') + assert feat.attributes['NAME'] == u'United States' def test_map_query_in_pixels_works1(): m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/wgs842merc_reprojection.xml') + mapnik.load_map(m, './test/data/good_maps/wgs842merc_reprojection.xml') merc_bounds = mapnik.Box2d(-20037508.34, - 20037508.34, 20037508.34, 20037508.34) m.maximum_extent = merc_bounds m.zoom_all() fs = m.query_map_point(0, 55, 100) # somewhere in middle of us feat = fs.next() - eq_(feat.attributes['NAME_FORMA'], u'United States of America') + assert feat.attributes['NAME_FORMA'] == u'United States of America' def test_map_query_in_pixels_works2(): m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/merc2wgs84_reprojection.xml') + mapnik.load_map(m, './test/data/good_maps/merc2wgs84_reprojection.xml') wgs84_bounds = mapnik.Box2d(-179.999999975, - 85.0511287776, 179.999999975, 85.0511287776) m.maximum_extent = wgs84_bounds @@ -107,14 +88,10 @@ def test_map_query_in_pixels_works2(): m.zoom_all() # validate that aspect_fix_mode modified the bbox reasonably e = m.envelope() - assert_almost_equal(e.minx, -179.999999975, places=7) - assert_almost_equal(e.miny, -167.951396161, places=7) - assert_almost_equal(e.maxx, 179.999999975, places=7) - assert_almost_equal(e.maxy, 192.048603789, places=7) + assert e.minx == pytest.approx(-179.999999975, abs=1e-7) + assert e.miny == pytest.approx(-167.951396161, abs=1e-7) + assert e.maxx == pytest.approx(179.999999975, abs=1e-7) + assert e.maxy == pytest.approx(192.048603789, abs=1e-7) fs = m.query_map_point(0, 55, 100) # somewhere in Canada feat = fs.next() - eq_(feat.attributes['NAME'], u'Canada') - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert feat.attributes['NAME'] == u'Canada' From 114bab7a307e3d43d4659db397b3547cb64148d2 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 1 Feb 2023 16:05:34 +0000 Subject: [PATCH 07/37] Add `keys()` method returning `boost::python::list` e.g ``` >>> import mapnik >>> sym = mapnik.PolygonSymbolizer() >>> sym.keys() [] >>> sym.fill = mapnik.Color("skyblue") >>> sym.fill_opacity = 0.7 >>> sym.keys() ['fill', 'fill-opacity'] ``` --- src/mapnik_symbolizer.cpp | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/src/mapnik_symbolizer.cpp b/src/mapnik_symbolizer.cpp index 36f414b32..286b11af1 100644 --- a/src/mapnik_symbolizer.cpp +++ b/src/mapnik_symbolizer.cpp @@ -196,6 +196,17 @@ boost::python::object __getitem__(mapnik::symbolizer_base const& sym, std::strin return boost::python::object(); } +boost::python::object symbolizer_keys(mapnik::symbolizer_base const& sym) +{ + using const_iterator = symbolizer_base::cont_type::const_iterator; + boost::python::list keys; + for (auto const& kv : sym.properties) + { + std::string name = std::get<0>(mapnik::get_meta(kv.first)); + keys.append(name); + } + return keys; +} /* std::string __str__(mapnik::symbolizer const& sym) { @@ -268,6 +279,7 @@ void export_symbolizer() .def("__setattr__",&__setitem__) .def("__getitem__",&__getitem__) .def("__getattr__",&__getitem__) + .def("keys", &symbolizer_keys) //.def("__str__", &__str__) .def(self == self) // __eq__ ; From 2a92ab0638bca833f7556ee78536fea8ec123e71 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 1 Feb 2023 16:07:19 +0000 Subject: [PATCH 08/37] Unit tests - 'pytest` [WIP] --- test/python_tests/mapnik_logger_test.py | 21 +++----- test/python_tests/memory_datasource_test.py | 19 ++----- test/python_tests/multi_tile_raster_test.py | 53 +++++++------------- test/python_tests/my.pdf | Bin 7050 -> 0 bytes 4 files changed, 28 insertions(+), 65 deletions(-) delete mode 100644 test/python_tests/my.pdf diff --git a/test/python_tests/mapnik_logger_test.py b/test/python_tests/mapnik_logger_test.py index 8c6c5437a..7d7566890 100644 --- a/test/python_tests/mapnik_logger_test.py +++ b/test/python_tests/mapnik_logger_test.py @@ -1,21 +1,12 @@ -#!/usr/bin/env python -from nose.tools import eq_ - import mapnik -from .utilities import run_all - - def test_logger_init(): - eq_(mapnik.severity_type.Debug, 0) - eq_(mapnik.severity_type.Warn, 1) - eq_(mapnik.severity_type.Error, 2) - eq_(getattr(mapnik.severity_type, "None"), 3) + assert mapnik.severity_type.Debug == 0 + assert mapnik.severity_type.Warn == 1 + assert mapnik.severity_type.Error == 2 + assert getattr(mapnik.severity_type, "None") == 3 default = mapnik.logger.get_severity() mapnik.logger.set_severity(mapnik.severity_type.Debug) - eq_(mapnik.logger.get_severity(), mapnik.severity_type.Debug) + assert mapnik.logger.get_severity() == mapnik.severity_type.Debug mapnik.logger.set_severity(default) - eq_(mapnik.logger.get_severity(), default) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert mapnik.logger.get_severity() == default diff --git a/test/python_tests/memory_datasource_test.py b/test/python_tests/memory_datasource_test.py index d19dbb593..fbe1d8987 100644 --- a/test/python_tests/memory_datasource_test.py +++ b/test/python_tests/memory_datasource_test.py @@ -1,21 +1,15 @@ -# encoding: utf8 -from nose.tools import eq_ - import mapnik -from .utilities import run_all - - def test_add_feature(): md = mapnik.MemoryDatasource() - eq_(md.num_features(), 0) + assert md.num_features() == 0 context = mapnik.Context() context.push('foo') feature = mapnik.Feature(context, 1) feature['foo'] = 'bar' feature.geometry = mapnik.Geometry.from_wkt('POINT(2 3)') md.add_feature(feature) - eq_(md.num_features(), 1) + assert md.num_features() == 1 featureset = md.features_at_point(mapnik.Coord(2, 3)) retrieved = [] @@ -23,15 +17,12 @@ def test_add_feature(): for feat in featureset: retrieved.append(feat) - eq_(len(retrieved), 1) + assert len(retrieved) == 1 f = retrieved[0] - eq_(f['foo'], 'bar') + assert f['foo'] == 'bar' featureset = md.features_at_point(mapnik.Coord(20, 30)) retrieved = [] for feat in featureset: retrieved.append(feat) - eq_(len(retrieved), 0) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert len(retrieved) == 0 diff --git a/test/python_tests/multi_tile_raster_test.py b/test/python_tests/multi_tile_raster_test.py index 26fd68adc..5ec750dcd 100644 --- a/test/python_tests/multi_tile_raster_test.py +++ b/test/python_tests/multi_tile_raster_test.py @@ -1,26 +1,11 @@ -#!/usr/bin/env python - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def test_multi_tile_policy(): srs = 'epsg:4326' lyr = mapnik.Layer('raster') if 'raster' in mapnik.DatasourceCache.plugin_names(): lyr.datasource = mapnik.Raster( - file='../data/raster_tiles/${x}/${y}.tif', + file='./test/data/raster_tiles/${x}/${y}.tif', lox=-180, loy=-90, hix=180, @@ -46,29 +31,25 @@ def test_multi_tile_policy(): mapnik.render(_map, im) # test green chunk - eq_(im.view(0, 64, 1, 1).tostring(), b'\x00\xff\x00\xff') - eq_(im.view(127, 64, 1, 1).tostring(), b'\x00\xff\x00\xff') - eq_(im.view(0, 127, 1, 1).tostring(), b'\x00\xff\x00\xff') - eq_(im.view(127, 127, 1, 1).tostring(), b'\x00\xff\x00\xff') + assert im.view(0, 64, 1, 1).tostring() == b'\x00\xff\x00\xff' + assert im.view(127, 64, 1, 1).tostring() == b'\x00\xff\x00\xff' + assert im.view(0, 127, 1, 1).tostring() == b'\x00\xff\x00\xff' + assert im.view(127, 127, 1, 1).tostring() == b'\x00\xff\x00\xff' # test blue chunk - eq_(im.view(128, 64, 1, 1).tostring(), b'\x00\x00\xff\xff') - eq_(im.view(255, 64, 1, 1).tostring(), b'\x00\x00\xff\xff') - eq_(im.view(128, 127, 1, 1).tostring(), b'\x00\x00\xff\xff') - eq_(im.view(255, 127, 1, 1).tostring(), b'\x00\x00\xff\xff') + assert im.view(128, 64, 1, 1).tostring() == b'\x00\x00\xff\xff' + assert im.view(255, 64, 1, 1).tostring() == b'\x00\x00\xff\xff' + assert im.view(128, 127, 1, 1).tostring() == b'\x00\x00\xff\xff' + assert im.view(255, 127, 1, 1).tostring() == b'\x00\x00\xff\xff' # test red chunk - eq_(im.view(0, 128, 1, 1).tostring(), b'\xff\x00\x00\xff') - eq_(im.view(127, 128, 1, 1).tostring(), b'\xff\x00\x00\xff') - eq_(im.view(0, 191, 1, 1).tostring(), b'\xff\x00\x00\xff') - eq_(im.view(127, 191, 1, 1).tostring(), b'\xff\x00\x00\xff') + assert im.view(0, 128, 1, 1).tostring() == b'\xff\x00\x00\xff' + assert im.view(127, 128, 1, 1).tostring() == b'\xff\x00\x00\xff' + assert im.view(0, 191, 1, 1).tostring() == b'\xff\x00\x00\xff' + assert im.view(127, 191, 1, 1).tostring() == b'\xff\x00\x00\xff' # test magenta chunk - eq_(im.view(128, 128, 1, 1).tostring(), b'\xff\x00\xff\xff') - eq_(im.view(255, 128, 1, 1).tostring(), b'\xff\x00\xff\xff') - eq_(im.view(128, 191, 1, 1).tostring(), b'\xff\x00\xff\xff') - eq_(im.view(255, 191, 1, 1).tostring(), b'\xff\x00\xff\xff') - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im.view(128, 128, 1, 1).tostring() == b'\xff\x00\xff\xff' + assert im.view(255, 128, 1, 1).tostring() == b'\xff\x00\xff\xff' + assert im.view(128, 191, 1, 1).tostring() == b'\xff\x00\xff\xff' + assert im.view(255, 191, 1, 1).tostring() == b'\xff\x00\xff\xff' diff --git a/test/python_tests/my.pdf b/test/python_tests/my.pdf deleted file mode 100644 index 7d80dfdd8eea01477650579757c7bc2bb593d4ff..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 7050 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 a9>041L!1Bcu7B*k|9-E({Yw1e_5T1;UKNx8 From 6727f11801c60152071d13768408c558a60d6825 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Tue, 7 Feb 2023 13:49:10 +0000 Subject: [PATCH 09/37] Upgrade `ogr` and feature id unit tests --- test/python_tests/feature_id_test.py | 52 +-- .../ogr_and_shape_geometries_test.py | 30 +- test/python_tests/ogr_test.py | 359 ++++++------------ 3 files changed, 143 insertions(+), 298 deletions(-) diff --git a/test/python_tests/feature_id_test.py b/test/python_tests/feature_id_test.py index e8a5056a5..4f64b06ee 100644 --- a/test/python_tests/feature_id_test.py +++ b/test/python_tests/feature_id_test.py @@ -1,25 +1,11 @@ -#!/usr/bin/env python - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - try: import itertools.izip as zip except ImportError: pass -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - def compare_shape_between_mapnik_and_ogr(shapefile, query=None): plugins = mapnik.DatasourceCache.plugin_names() if 'shape' in plugins and 'ogr' in plugins: @@ -34,47 +20,39 @@ def compare_shape_between_mapnik_and_ogr(shapefile, query=None): count = 0 for feat1, feat2 in zip(fs1, fs2): count += 1 - eq_(feat1.id(), feat2.id(), - '%s : ogr feature id %s "%s" does not equal shapefile feature id %s "%s"' - % (count, feat1.id(), str(feat1.attributes), feat2.id(), str(feat2.attributes))) + assert feat1.id() == feat2.id(), '%s : ogr feature id %s "%s" does not equal shapefile feature id %s "%s"' % (count, feat1.id(), str(feat1.attributes), feat2.id(), str(feat2.attributes)) return True def test_shapefile_line_featureset_id(): - compare_shape_between_mapnik_and_ogr('../data/shp/polylines.shp') + compare_shape_between_mapnik_and_ogr('./test/data/shp/polylines.shp') def test_shapefile_polygon_featureset_id(): - compare_shape_between_mapnik_and_ogr('../data/shp/poly.shp') + compare_shape_between_mapnik_and_ogr('./test/data/shp/poly.shp') def test_shapefile_polygon_feature_query_id(): bbox = (15523428.2632, 4110477.6323, -11218494.8310, 7495720.7404) query = mapnik.Query(mapnik.Box2d(*bbox)) if 'ogr' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Ogr(file='../data/shp/world_merc.shp', layer_by_index=0) + ds = mapnik.Ogr(file='./test/data/shp/world_merc.shp', layer_by_index=0) for fld in ds.fields(): query.add_property_name(fld) compare_shape_between_mapnik_and_ogr( - '../data/shp/world_merc.shp', query) + './test/data/shp/world_merc.shp', query) def test_feature_hit_count(): - pass - #raise Todo("need to optimize multigeom bbox handling in shapeindex: https://github.com/mapnik/mapnik/issues/783") # results in different results between shp and ogr! #bbox = (-14284551.8434, 2074195.1992, -7474929.8687, 8140237.7628) - #bbox = (1113194.91,4512803.085,2226389.82,6739192.905) - #query = mapnik.Query(mapnik.Box2d(*bbox)) - # if 'ogr' in mapnik.DatasourceCache.plugin_names(): - # ds1 = mapnik.Ogr(file='../data/shp/world_merc.shp',layer_by_index=0) - # for fld in ds1.fields(): - # query.add_property_name(fld) - # ds2 = mapnik.Shapefile(file='../data/shp/world_merc.shp') - # count1 = len(ds1.features(query).features) - # count2 = len(ds2.features(query).features) - # eq_(count1,count2,"Feature count differs between OGR driver (%s features) and Shapefile Driver (%s features) when querying the same bbox" % (count1,count2)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + bbox = (1113194.91,4512803.085,2226389.82,6739192.905) + query = mapnik.Query(mapnik.Box2d(*bbox)) + if 'ogr' in mapnik.DatasourceCache.plugin_names(): + ds1 = mapnik.Ogr(file='./test/data/shp/world_merc.shp',layer_by_index=0) + for fld in ds1.fields(): + query.add_property_name(fld) + ds2 = mapnik.Shapefile(file='./test/data/shp/world_merc.shp') + count1 = len(list(ds1.features(query))) + count2 = len(list(ds2.features(query))) + assert count1 < count2 # expected 17 and 20 diff --git a/test/python_tests/ogr_and_shape_geometries_test.py b/test/python_tests/ogr_and_shape_geometries_test.py index 04fd62430..49644e9e8 100644 --- a/test/python_tests/ogr_and_shape_geometries_test.py +++ b/test/python_tests/ogr_and_shape_geometries_test.py @@ -1,24 +1,11 @@ -#!/usr/bin/env python - -import os - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - try: import itertools.izip as zip except ImportError: pass -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - # TODO - fix truncation in shapefile... polys = ["POLYGON ((30 10, 10 20, 20 40, 40 40, 30 10))", "POLYGON ((35 10, 10 20, 15 40, 45 45, 35 10),(20 30, 35 35, 30 20, 20 30))", @@ -37,17 +24,12 @@ def ensure_geometries_are_interpreted_equivalently(filename): count = 0 for feat1, feat2 in zip(fs1, fs2): count += 1 - eq_(feat1.attributes, feat2.attributes) - # TODO - revisit this: https://github.com/mapnik/mapnik/issues/1093 - # eq_(feat1.to_geojson(),feat2.to_geojson()) - # eq_(feat1.geometries().to_wkt(),feat2.geometries().to_wkt()) - # eq_(feat1.geometries().to_wkb(mapnik.wkbByteOrder.NDR),feat2.geometries().to_wkb(mapnik.wkbByteOrder.NDR)) - # eq_(feat1.geometries().to_wkb(mapnik.wkbByteOrder.XDR),feat2.geometries().to_wkb(mapnik.wkbByteOrder.XDR)) + assert feat1.attributes == feat2.attributes + assert feat1.to_geojson() == feat2.to_geojson() + assert feat1.geometry.to_wkt() == feat2.geometry.to_wkt() + assert feat1.geometry.to_wkb(mapnik.wkbByteOrder.NDR) == feat2.geometry.to_wkb(mapnik.wkbByteOrder.NDR) + assert feat1.geometry.to_wkb(mapnik.wkbByteOrder.XDR) == feat2.geometry.to_wkb(mapnik.wkbByteOrder.XDR) def test_simple_polys(): ensure_geometries_are_interpreted_equivalently( - '../data/shp/wkt_poly.shp') - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + './test/data/shp/wkt_poly.shp') diff --git a/test/python_tests/ogr_test.py b/test/python_tests/ogr_test.py index bc527a6cf..b35f80f7e 100644 --- a/test/python_tests/ogr_test.py +++ b/test/python_tests/ogr_test.py @@ -1,306 +1,191 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - -from nose.tools import assert_almost_equal, eq_, raises - import mapnik - -from .utilities import execution_path, run_all +import pytest try: import json except ImportError: import simplejson as json - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - if 'ogr' in mapnik.DatasourceCache.plugin_names(): # Shapefile initialization def test_shapefile_init(): - ds = mapnik.Ogr(file='../data/shp/boundaries.shp', layer_by_index=0) + ds = mapnik.Ogr(file='./test/data/shp/boundaries.shp', layer_by_index=0) e = ds.envelope() - assert_almost_equal(e.minx, -11121.6896651, places=7) - assert_almost_equal(e.miny, -724724.216526, places=6) - assert_almost_equal(e.maxx, 2463000.67866, places=5) - assert_almost_equal(e.maxy, 1649661.267, places=3) + assert e.minx == pytest.approx(-11121.6896651, abs=1e-7) + assert e.miny == pytest.approx(-724724.216526, abs=1e-6) + assert e.maxx == pytest.approx(2463000.67866, abs=1e-5) + assert e.maxy == pytest.approx(1649661.267, abs=1e-3) meta = ds.describe() - eq_(meta['geometry_type'], mapnik.DataGeometryType.Polygon) - eq_('+proj=lcc' in meta['proj'], True) + assert meta['geometry_type'] == mapnik.DataGeometryType.Polygon + assert '+proj=lcc' in meta['proj4'] # Shapefile properties def test_shapefile_properties(): - ds = mapnik.Ogr(file='../data/shp/boundaries.shp', layer_by_index=0) + ds = mapnik.Ogr(file='./test/data/shp/boundaries.shp', layer_by_index=0) f = list(ds.features_at_point(ds.envelope().center(), 0.001))[0] - eq_(ds.geometry_type(), mapnik.DataGeometryType.Polygon) - - eq_(f['CGNS_FID'], u'6f733341ba2011d892e2080020a0f4c9') - eq_(f['COUNTRY'], u'CAN') - eq_(f['F_CODE'], u'FA001') - eq_(f['NAME_EN'], u'Quebec') - eq_(f['Shape_Area'], 1512185733150.0) - eq_(f['Shape_Leng'], 19218883.724300001) + assert ds.geometry_type() == mapnik.DataGeometryType.Polygon + + assert f['CGNS_FID'] == u'6f733341ba2011d892e2080020a0f4c9' + assert f['COUNTRY'] == u'CAN' + assert f['F_CODE'] == u'FA001' + assert f['NAME_EN'] == u'Quebec' + assert f['Shape_Area'] == 1512185733150.0 + assert f['Shape_Leng'] == 19218883.724300001 meta = ds.describe() - eq_(meta['geometry_type'], mapnik.DataGeometryType.Polygon) - # NOTE: encoding is latin1 but gdal >= 1.9 should now expose utf8 encoded features - # See SHAPE_ENCODING for overriding: http://gdal.org/ogr/drv_shapefile.html - # Failure for the NOM_FR field is expected for older gdal - #eq_(f['NOM_FR'], u'Qu\xe9bec') - #eq_(f['NOM_FR'], u'Québec') + assert meta['geometry_type'] == mapnik.DataGeometryType.Polygon + assert f['NOM_FR'] == u'Qu\xe9bec' + assert f['NOM_FR'] == u'Québec' - @raises(RuntimeError) def test_that_nonexistant_query_field_throws(**kwargs): - ds = mapnik.Ogr(file='../data/shp/world_merc.shp', layer_by_index=0) - eq_(len(ds.fields()), 11) - eq_(ds.fields(), ['FIPS', 'ISO2', 'ISO3', 'UN', 'NAME', - 'AREA', 'POP2005', 'REGION', 'SUBREGION', 'LON', 'LAT']) - eq_(ds.field_types(), - ['str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float']) - query = mapnik.Query(ds.envelope()) - for fld in ds.fields(): - query.add_property_name(fld) - # also add an invalid one, triggering throw - query.add_property_name('bogus') - ds.features(query) + with pytest.raises(RuntimeError): + ds = mapnik.Ogr(file='./test/data/shp/world_merc.shp', layer_by_index=0) + assert len(ds.fields()) == 11 + assert ds.fields() == ['FIPS', 'ISO2', 'ISO3', 'UN', 'NAME', + 'AREA', 'POP2005', 'REGION', 'SUBREGION', 'LON', 'LAT'] + assert ds.field_types() == ['str','str','str','int','str','int','int','int','int','float','float'] + query = mapnik.Query(ds.envelope()) + for fld in ds.fields(): + query.add_property_name(fld) + # also add an invalid one, triggering throw + query.add_property_name('bogus') + ds.features(query) # disabled because OGR prints an annoying error: ERROR 1: Invalid Point object. Missing 'coordinates' member. # def test_handling_of_null_features(): - # ds = mapnik.Ogr(file='../data/json/null_feature.geojson',layer_by_index=0) - # fs = ds.all_features() - # eq_(len(fs),1) + # ds = mapnik.Ogr(file='./test/data/json/null_feature.geojson',layer_by_index=0) + # fs = ds.all_features() + # assert len(list(fs)) == 1 # OGR plugin extent parameter def test_ogr_extent_parameter(): ds = mapnik.Ogr( - file='../data/shp/world_merc.shp', + file='./test/data/shp/world_merc.shp', layer_by_index=0, extent='-1,-1,1,1') e = ds.envelope() - eq_(e.minx, -1) - eq_(e.miny, -1) - eq_(e.maxx, 1) - eq_(e.maxy, 1) + assert e.minx == -1 + assert e.miny == -1 + assert e.maxx == 1 + assert e.maxy == 1 meta = ds.describe() - eq_(meta['geometry_type'], mapnik.DataGeometryType.Polygon) - eq_('+proj=merc' in meta['proj'], True) + assert meta['geometry_type'] == mapnik.DataGeometryType.Polygon + assert '+proj=merc' in meta['proj4'] def test_ogr_reading_gpx_waypoint(): - ds = mapnik.Ogr(file='../data/gpx/empty.gpx', layer='waypoints') + ds = mapnik.Ogr(file='./test/data/gpx/empty.gpx', layer='waypoints') e = ds.envelope() - eq_(e.minx, -122) - eq_(e.miny, 48) - eq_(e.maxx, -122) - eq_(e.maxy, 48) + assert e.minx == -122 + assert e.miny == 48 + assert e.maxx == -122 + assert e.maxy == 48 meta = ds.describe() - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) - eq_('+proj=longlat' in meta['proj'], True) + assert meta['geometry_type'] == mapnik.DataGeometryType.Point + assert '+proj=longlat' in meta['proj4'] def test_ogr_empty_data_should_not_throw(): default_logging_severity = mapnik.logger.get_severity() mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) # use logger to silence expected warnings for layer in ['routes', 'tracks', 'route_points', 'track_points']: - ds = mapnik.Ogr(file='../data/gpx/empty.gpx', layer=layer) + ds = mapnik.Ogr(file='./test/data/gpx/empty.gpx', layer=layer) e = ds.envelope() - eq_(e.minx, 0) - eq_(e.miny, 0) - eq_(e.maxx, 0) - eq_(e.maxy, 0) + assert e.minx == 0 + assert e.miny == 0 + assert e.maxx == 0 + assert e.maxy == 0 mapnik.logger.set_severity(default_logging_severity) meta = ds.describe() - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) - eq_('+proj=longlat' in meta['proj'], True) + assert meta['geometry_type'] == mapnik.DataGeometryType.Point + assert '+proj=longlat' in meta['proj4'] # disabled because OGR prints an annoying error: ERROR 1: Invalid Point object. Missing 'coordinates' member. - # def test_handling_of_null_features(): - # ds = mapnik.Ogr(file='../data/json/null_feature.geojson',layer_by_index=0) - # fs = ds.all_features() - # eq_(len(fs),1) + def test_handling_of_null_features(): + assert True + ds = mapnik.Ogr(file='./test/data/json/null_feature.geojson',layer_by_index=0) + fs = ds.all_features() + assert len(list(fs)) == 1 def test_geometry_type(): - ds = mapnik.Ogr(file='../data/csv/wkt.csv', layer_by_index=0) + ds = mapnik.Ogr(file='./test/data/csv/wkt.csv', layer_by_index=0) e = ds.envelope() - assert_almost_equal(e.minx, 1.0, places=1) - assert_almost_equal(e.miny, 1.0, places=1) - assert_almost_equal(e.maxx, 45.0, places=1) - assert_almost_equal(e.maxy, 45.0, places=1) + assert e.minx == pytest.approx(1.0, abs=1e-1) + assert e.miny == pytest.approx(1.0, abs=1e-1) + assert e.maxx == pytest.approx(45.0, abs=1e-1) + assert e.maxy == pytest.approx(45.0, abs=1e-1) meta = ds.describe() - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) - #eq_('+proj=longlat' in meta['proj'],True) + assert meta['geometry_type'] == mapnik.DataGeometryType.Point fs = ds.featureset() feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, - {u'geometry': {u'type': u'Point', - u'coordinates': [30, - 10]}, - u'type': u'Feature', - u'id': 2, - u'properties': {u'type': u'point', - u'WKT': u' POINT (30 10)'}}) + assert actual == {u'geometry': {u'type': u'Point', + u'coordinates': [30,10]}, + u'type': u'Feature', + u'id': 2, + u'properties': {u'type': u'point', + u'WKT': u' POINT (30 10)'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, - {u'geometry': {u'type': u'LineString', - u'coordinates': [[30, - 10], - [10, - 30], - [40, - 40]]}, - u'type': u'Feature', - u'id': 3, - u'properties': {u'type': u'linestring', - u'WKT': u' LINESTRING (30 10, 10 30, 40 40)'}}) + assert actual == {u'geometry': {u'type': u'LineString', + u'coordinates': [[30,10],[10,30],[40,40]]}, + u'type': u'Feature', + u'id': 3, + u'properties': {u'type': u'linestring', + u'WKT': u' LINESTRING (30 10, 10 30, 40 40)'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, - {u'geometry': {u'type': u'Polygon', - u'coordinates': [[[30, - 10], - [40, - 40], - [20, - 40], - [10, - 20], - [30, - 10]]]}, - u'type': u'Feature', - u'id': 4, - u'properties': {u'type': u'polygon', - u'WKT': u' POLYGON ((30 10, 10 20, 20 40, 40 40, 30 10))'}}) + assert actual == {u'geometry': {u'type': u'Polygon', u'coordinates': [[[30,10],[40,40],[20,40],[10,20],[30,10]]]}, + u'type': u'Feature', + u'id': 4, + u'properties': {u'type': u'polygon', + u'WKT': u' POLYGON ((30 10, 10 20, 20 40, 40 40, 30 10))'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_( - actual, { - u'geometry': { - u'type': u'Polygon', u'coordinates': [ - [ - [ - 35, 10], [ - 45, 45], [ - 15, 40], [ - 10, 20], [ - 35, 10]], [ - [ - 20, 30], [ - 35, 35], [ - 30, 20], [ - 20, 30]]]}, u'type': u'Feature', u'id': 5, u'properties': { - u'type': u'polygon', u'WKT': u' POLYGON ((35 10, 10 20, 15 40, 45 45, 35 10),(20 30, 35 35, 30 20, 20 30))'}}) + assert actual == {u'geometry': {u'type': u'Polygon', u'coordinates': [[[35, 10],[45,45],[15,40],[10,20],[35,10]],[[20,30],[35,35],[30,20],[20,30]]]}, + u'type': u'Feature', + u'id': 5, + u'properties': { u'type': u'polygon', u'WKT': u' POLYGON ((35 10, 10 20, 15 40, 45 45, 35 10),(20 30, 35 35, 30 20, 20 30))'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, - {u'geometry': {u'type': u'MultiPoint', - u'coordinates': [[10, - 40], - [40, - 30], - [20, - 20], - [30, - 10]]}, - u'type': u'Feature', - u'id': 6, - u'properties': {u'type': u'multipoint', - u'WKT': u' MULTIPOINT ((10 40), (40 30), (20 20), (30 10))'}}) + assert actual == {u'geometry': {u'type': u'MultiPoint', + u'coordinates': [[10,40],[40,30],[20,20],[30,10]]}, + u'type': u'Feature', + u'id': 6, + u'properties': {u'type': u'multipoint', + u'WKT': u' MULTIPOINT ((10 40), (40 30), (20 20), (30 10))'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, - {u'geometry': {u'type': u'MultiLineString', - u'coordinates': [[[10, - 10], - [20, - 20], - [10, - 40]], - [[40, - 40], - [30, - 30], - [40, - 20], - [30, - 10]]]}, - u'type': u'Feature', - u'id': 7, - u'properties': {u'type': u'multilinestring', - u'WKT': u' MULTILINESTRING ((10 10, 20 20, 10 40),(40 40, 30 30, 40 20, 30 10))'}}) + assert actual == {u'geometry': {u'type': u'MultiLineString', + u'coordinates': [[[10,10],[20,20],[10,40]],[[40,40],[30,30],[40,20],[30,10]]]}, + u'type': u'Feature', + u'id': 7, + u'properties': {u'type': u'multilinestring', + u'WKT': u' MULTILINESTRING ((10 10, 20 20, 10 40),(40 40, 30 30, 40 20, 30 10))'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, - {u'geometry': {u'type': u'MultiPolygon', - u'coordinates': [[[[30, - 20], - [45, - 40], - [10, - 40], - [30, - 20]]], - [[[15, - 5], - [40, - 10], - [10, - 20], - [5, - 10], - [15, - 5]]]]}, - u'type': u'Feature', - u'id': 8, - u'properties': {u'type': u'multipolygon', - u'WKT': u' MULTIPOLYGON (((30 20, 10 40, 45 40, 30 20)),((15 5, 40 10, 10 20, 5 10, 15 5)))'}}) + assert actual == {u'geometry': {u'type': u'MultiPolygon', + u'coordinates': [[[[30,20],[45,40],[10,40],[30,20]]],[[[15,5],[40,10],[10,20],[5,10],[15,5]]]]}, + u'type': u'Feature', + u'id': 8, + u'properties': {u'type': u'multipolygon', + u'WKT': u' MULTIPOLYGON (((30 20, 10 40, 45 40, 30 20)),((15 5, 40 10, 10 20, 5 10, 15 5)))'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, {u'geometry': {u'type': u'MultiPolygon', u'coordinates': [[[[40, 40], [20, 45], [45, 30], [40, 40]]], [[[20, 35], [10, 30], [10, 10], [30, 5], [45, 20], [20, 35]], [[30, 20], [20, 15], [20, 25], [ - 30, 20]]]]}, u'type': u'Feature', u'id': 9, u'properties': {u'type': u'multipolygon', u'WKT': u' MULTIPOLYGON (((40 40, 20 45, 45 30, 40 40)),((20 35, 45 20, 30 5, 10 10, 10 30, 20 35),(30 20, 20 25, 20 15, 30 20)))'}}) + assert actual == {u'geometry': {u'type': u'MultiPolygon', + u'coordinates': [[[[40, 40], [20, 45], [45, 30], [40, 40]]], [[[20, 35], [10, 30], [10, 10], [30, 5], [45, 20], [20, 35]], [[30, 20], [20, 15], [20, 25], [30, 20]]]]}, + u'type': u'Feature', + u'id': 9, + u'properties': {u'type': u'multipolygon', u'WKT': u' MULTIPOLYGON (((40 40, 20 45, 45 30, 40 40)),((20 35, 45 20, 30 5, 10 10, 10 30, 20 35),(30 20, 20 25, 20 15, 30 20)))'}} feat = fs.next() actual = json.loads(feat.to_geojson()) - eq_(actual, - {u'geometry': {u'type': u'GeometryCollection', - u'geometries': [{u'type': u'Polygon', - u'coordinates': [[[1, - 1], - [2, - 1], - [2, - 2], - [1, - 2], - [1, - 1]]]}, - {u'type': u'Point', - u'coordinates': [2, - 3]}, - {u'type': u'LineString', - u'coordinates': [[2, - 3], - [3, - 4]]}]}, - u'type': u'Feature', - u'id': 10, - u'properties': {u'type': u'collection', - u'WKT': u' GEOMETRYCOLLECTION(POLYGON((1 1,2 1,2 2,1 2,1 1)),POINT(2 3),LINESTRING(2 3,3 4))'}}) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert actual == {u'geometry': {u'type': u'GeometryCollection', + u'geometries': [{u'type': u'Polygon', + u'coordinates': [[[1, 1],[2,1],[2,2],[1,2],[1,1]]]}, + {u'type': u'Point', + u'coordinates': [2,3]}, + {u'type': u'LineString', + u'coordinates': [[2,3],[3,4]]}]}, + u'type': u'Feature', + u'id': 10, + u'properties': {u'type': u'collection', + u'WKT': u' GEOMETRYCOLLECTION(POLYGON((1 1,2 1,2 2,1 2,1 1)),POINT(2 3),LINESTRING(2 3,3 4))'}} From d6e8d1b3e03e8ed28925b24cc51e2c1089f04a6c Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Tue, 7 Feb 2023 14:24:15 +0000 Subject: [PATCH 10/37] Unit tests - markers + image-filters [WIP] --- test/python_tests/image_filters_test.py | 37 ++---- .../style-image-filter/agg-stack-blur22.png | Bin 33686 -> 33675 bytes .../images/style-image-filter/blur.png | Bin 27207 -> 27215 bytes .../images/style-image-filter/edge-detect.png | Bin 22471 -> 22468 bytes .../images/style-image-filter/emboss.png | Bin 24552 -> 24534 bytes .../images/style-image-filter/gray.png | Bin 23599 -> 23577 bytes .../images/style-image-filter/invert.png | Bin 24136 -> 24127 bytes .../images/style-image-filter/none.png | Bin 24079 -> 24056 bytes .../images/style-image-filter/sharpen.png | Bin 22760 -> 22744 bytes .../images/style-image-filter/sobel.png | Bin 23955 -> 23931 bytes .../images/style-image-filter/x-gradient.png | Bin 27060 -> 27039 bytes .../images/style-image-filter/y-gradient.png | Bin 27268 -> 27260 bytes .../marker-text-line-scale-factor-0.1.png | Bin 3845 -> 3778 bytes .../marker-text-line-scale-factor-0.899.png | Bin 17232 -> 17257 bytes .../marker-text-line-scale-factor-1.5.png | Bin 11508 -> 11456 bytes .../marker-text-line-scale-factor-1.png | Bin 18310 -> 18307 bytes .../marker-text-line-scale-factor-10.png | Bin 8369 -> 8392 bytes .../marker-text-line-scale-factor-2.png | Bin 11838 -> 11847 bytes .../marker-text-line-scale-factor-5.png | Bin 13978 -> 13953 bytes test/python_tests/render_test.py | 124 ++++++------------ 20 files changed, 51 insertions(+), 110 deletions(-) diff --git a/test/python_tests/image_filters_test.py b/test/python_tests/image_filters_test.py index 7a06db3fd..c61da73d6 100644 --- a/test/python_tests/image_filters_test.py +++ b/test/python_tests/image_filters_test.py @@ -1,38 +1,23 @@ -#!/usr/bin/env python - -import os -import re - -from nose.tools import eq_ - +import re, os import mapnik - -from .utilities import execution_path, run_all, side_by_side_image - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - +from .utilities import side_by_side_image def replace_style(m, name, style): m.remove_style(name) m.append_style(name, style) - def test_append(): s = mapnik.Style() - eq_(s.image_filters, '') + assert s.image_filters == '' s.image_filters = 'gray' - eq_(s.image_filters, 'gray') + assert s.image_filters == 'gray' s.image_filters = 'sharpen' - eq_(s.image_filters, 'sharpen') + assert s.image_filters == 'sharpen' if 'shape' in mapnik.DatasourceCache.plugin_names(): def test_style_level_image_filter(): m = mapnik.Map(256, 256) - mapnik.load_map(m, '../data/good_maps/style_level_image_filter.xml') + mapnik.load_map(m, './test/data/good_maps/style_level_image_filter.xml') m.zoom_all() successes = [] fails = [] @@ -54,7 +39,7 @@ def test_style_level_image_filter(): im = mapnik.Image(m.width, m.height) mapnik.render(m, im) actual = '/tmp/mapnik-style-image-filter-' + filename + '.png' - expected = 'images/style-image-filter/' + filename + '.png' + expected = './test/python_tests/images/style-image-filter/' + filename + '.png' im.save(actual, "png32") if not os.path.exists(expected) or os.environ.get('UPDATE'): print('generating expected test image: %s' % expected) @@ -66,15 +51,11 @@ def test_style_level_image_filter(): else: fails.append( 'failed comparing actual (%s) and expected(%s)' % - (actual, 'tests/python_tests/' + expected)) + (actual, expected)) fail_im = side_by_side_image(expected_im, im) fail_im.save( '/tmp/mapnik-style-image-filter-' + filename + '.fail.png', 'png32') - eq_(len(fails), 0, '\n' + '\n'.join(fails)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert len(fails) == 0, '\n' + '\n'.join(fails) diff --git a/test/python_tests/images/style-image-filter/agg-stack-blur22.png b/test/python_tests/images/style-image-filter/agg-stack-blur22.png index 54f92eaf09f76d478be7ce722c0d16436f279188..b8226452eef5320fef45dd86f1ff35e67113ea1b 100644 GIT binary patch literal 33675 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 LNkvXXu0mjf+A3R9 literal 33686 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 diff --git a/test/python_tests/images/style-image-filter/blur.png b/test/python_tests/images/style-image-filter/blur.png index dfda77eb83716f596d8bc935653774b24b2ca4d8..29b72bfc382ed4b08dbef582a4a5371035df8c12 100644 GIT binary patch literal 27215 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�N^e50Pp*!}@n-nrl#xuf5sbaask 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 diff --git a/test/python_tests/images/style-image-filter/edge-detect.png b/test/python_tests/images/style-image-filter/edge-detect.png index 825b43cdf5b58c9d19f52cfa14017f3e3a169fe1..2c7cb146667c27995e23148fbe49767af5922539 100644 GIT binary patch literal 22468 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 Zcm-oJRb;3wlyU$7002ovPDHLkV1l*0jE4XK literal 22471 zcmXtfWmsHI6XoFU4#C~s9Rh^l3GRbyaCZ+uL$KiP?mkF@yGyVacN<)0hi`X(G0(%j z-CbQ>eXGtn6|JtSfPqSi3IG5w6hD3Z0sz23f5HHe5utw!UCXQh0G)WnkJ6gnS*O_u zhMFrxL)-uuoFk4SOgMZ5GJ|>qgSxu9HBfZikM;F+1W&Jf{gdO0%$m+~QV>McE8QjX zHw@xWB;Tm1`vJcjyZs4Kkl%Ux!A52C?E}`9^LIF%9O^6Zho+5Hl7-Yond$MQOU3K3 zXMDBTjUGer)X<1e)1Nm$R@dMEewAN-zLt+xq_=ngv&SUGk`Qz=kkT4n%KsD0cP*j}(cAJ;B-gT3HMiP(lU<bRh3PBq;mZxn-z2=N&#cj%1&`6aNFBaNK}6_ zPCFyX$avxmvt{#V(EebH`)^ouZ>$pQjE7oK%jxgkh=*>ty4^d~tiaa~rMWK*qE>4t zSCWDX{DuG_QWx+!E4r|V2K84iagJYx>H)Tn=psTWL+7ABVOY7&w+XF6t_Sojdm$IS zkLW~zc=->V5LCBX$67@MWv1Ci%7l>Xg*D+=mPY$wxx^+W}N?_#tf5o&YCc zD9DB}-n~2V;wEY#Z(ybG^Y7{2=`_d%BZWvIP|w*}o(gwg74P*q01Ik|KTh1fSMVC0 zU{Oy;+#g=IEs4M43TALHb75Q_JE}9F%~t4UOcFJM$EC+X^}<82VP8g7%R`GhIlsTX z_EPaUrr6{=F=Md%quzeCLiaXrAFo;A0Fe)s&J_%H?)%@Op-CFPdFvz*W@O1yI z4L#B$+}gQ9VP6_$UB@4c7&>Y46dl1iVrt-vyXt;~;9rH~q8(8l7?aF6OzTmD)Lm>( z_fP+O%>@^W18Cc`!tc9;a_*c-Wvk*$ei7d@@(=Do|J@b>T+jH)7C`t!wAA0bY7LPN zoR1wjWd$k2_@F<&cxE^F@!2?ZiCAX(cyOyXs2b4g%p z*K0F@*ickN!P3eOumx-P7JO>59ja>?L$^a6W1QS($2@EjFW+NA5Z~9SwV2%%KJBwd zukotLK^)*-qQBEhX@ga|x319@$sJosHc*s-;?EkHuh&VT7aUFvGw~m8-P`O`dgpoF z;ikA`FGBFmf}T4YLeJbw`p?#EG2Qa=Y1=A1HUoqHqLx3GF*@uV13i(vc7pb4ayW@n z6f!3@uUw|54h~}eO5ls!w09p6l$6u}c`>6@Dk6_c7e`_@YZAzn?K6AZA`7<1cJz3$ zRn|P0KEZ$2HhKasw?(Ie>=O<*C2QXuWRL!j_cuvEBeOVma~r>d-%5X5hWfEWgc~|=5Tpybf2uY0uYa(daJV7pE#7Z+hJ|r*F!poDItH; zCNWNR()enoA)%FR6hkNb?z!jUvzC!B!<4cAx%iTZaQSPT$jt&z78X1ZMan z`X|1Zej4=(JB&NMKRuK_FdTp^L!j(2JD5Cu7}v81QLofTROkVzx7orLLAH9G0kNg| zj6QPe8a5WFIf5*wL=e%_DuK=xx4nCevDvF0;)=|K_apK0xJ<7TrNB%i->0eoo6o5> zi|=D@gv77qdpQTF;mOP1yAr7vopD-77dB1ov?c88?8H`-dqvrp;?s`9Tuo<-L>?JU zvbVnM(;v%F`3?zbnXg!hqNEdHek4!J;-t|q{a1wq=Z4qj`#8W@r%al!jP4IRutoME z^!qR(Pi>x7+QuQbgOI+*NwM=faUb6A9*5S$dwuBKyKVv>dZHlg;xWd&3Hei}JLz5L zvqafWGc}ptGyRdz7>c+M$0eiLhbZbC(L6V>TZ%_pF!Y^S#tw=x#g6~o43dk=Z1w^4 z_4Q*z5zq?!vssw5TZqA8w{(Lh1<10XaETuonf(KTx~c#P+FR7nfqsor7lWn~VL+T; zQ;1Iyf=s5S)-Ykw6y4ngqktjcT3D7aCzYfq`L{vCribVB%h%5bv>JJiuLs$ht1T94 z``^GFVS>{%J-PZYWou2@;}6A$gzT{5X*4_oX+yn}$i{EQny9_jqkWQe_#Ozg1^Q8u zRU$y`^$(Wzi>WAp0EQFV-??~J6Iw~z<6*gqIBA85`}@`YA#`TQh@@2J;A_-qA=WCL`9fx zjiLKIo#24W|B3{h=@*Iuf2On$wt#eDcKYLHT&a$86UQobv97Kqtkgu&>e3>dpY%`f z!W@=Jhnz*^h1iH*gW)Ho;w#=Pu<6cjQZyhLm=hdyX-%_bI7D!3Znkn; zXzpir-CrxXLG?=E)?#En{Yv!gqk%va>_7g8pU5)uVG49XfZk|*tx-IypK}Lml!RHi z&Jo0+(xP}IcI(D3GuBllb5v7ZNK0(<{Y$wTpB~Pye83?RS^xB3LU}^MOH8Kf#Rrvf zHjO%UYJ4VjKtyvhj=BiG>aCL0rW)lc;%ZffMwv6PEmDA>LPL0yuFW6f7;*eXL0XJI zE^`+V>P7DL-Ou(jFGJ(Vt7Bv&e1zF7wAW-EtsF$Tx@@Q)f{tnEpK&oi@g$BCrB~Llf z^om$w_o+>;DD!Bn@l6A2paOD>=F2mcnP5Nt{UI}z$Alh3pkUD%Qnu;Xr4K{JG$=(w6@)Q{nOgN+ z4_q-zx>s(-o@ddJt9}?|RgK?1q3I^D=e`jx%XR zr&uITvAv6?W7Qxfb$()SCMe`D-cH znhEeEhp~Vv)hHlNU+l3h!vn*#F;BXxy{ZgACBu)*sh7ZmCF11dTNR}&wx16P8d0Z* z$$J82|6;wt-K~`_mV9lsF=zIf(nkyZP*FWP97Emx=Kt(eVw@@hlPC$<9+Rx--Ve)t zGhN`6@EYwRyqXu4LpvXI~ za4id`CZb3+cc{!wvf>a1NW$3|*fm;`dLV#Y?`5N5u z_^`y58?+WpiNDy~q)ZUo;|z?3@jMrmmxed%xKAcwK?(kqKm;cL(QqnRII3NDvVbcR z>C04AiBTwjH%+)yE_)RIIcsA+NU2X&F9zw9R^rw8x zT!Not$Ko3)chA%I2jx+p52(wI_;{y6&;U{S9KlOolP-FdfRqnMl^^NSBksQ{LvI$FA=grOeHt+VJ_W_5J9yOW)d@V%=u zB$503b>K^d!WBQDdJ}PMRm7|b2pcb0<}Yf#w>hg`N`9RlaO4rqhPpzFvBj{$!SaxB zW?&d^ZpF90&aCeEK@VDj1gUVK_a$YQx@iK2*OEYj*DtTCv+hbXs_pnrZ*OWXXH8pg zUmK~Rbq=g1i+g(61C_>lmf@_A9jvd}*J0r=mW_t;het$~u-NJyY@fA|!*ufKZd-vD z7R#c-g>BI&=rLs6IMXfDkw8nl6j)P(RTa<495`IdF*-o%86E6a{W2T}uOZ#q%kh30 zKwU8><#o1}5_E@W<=8z6EoR1JCvzj{!{ zy9ZBGA=fu6@4V*WuJLh-iakZ}BQ=`(XB_c>Was;z2)F+}`|=KWqFu_ik7~{MZ^Pm@ zbBDJ?3sg=KIRV*^nCJ)qZqWezX?DQe>>UfjU|S3KX_S!Em@b;UM_f7*m2F^?HcR~+ z8A|}8$6C3McA!xYhgzSG#}K_^TUI{Ra1a9r;6vOpoj1}6? z0K}oWEwW0^ZYX3BJP1>^Nt4?CwpTe1JnB5kyk&~1O*h~s_DkXF=!{Tm7&X*g2X3C`VPlwosh^XvEfbrCWTZ zxOR(j%$Yx`TYRB0t^O4FWFtY3T+ZV#N|^^Z2ejKQy}7C3PqN|xHc)#fz1bM9LubBOC=bxd|tkxKRT_Wwm|Obr1e))tz;3*_8! zxigitP4JNS`(y>8PpgJ>$xQ(1)^q&#CDXjT#GGRL2UVAIKWADS0%l$Fe${uT5NbJWauY4Q~C zUc%Y{5;Ee<=KWv-jjMhqkbvxQ4%6)``2w{LMGgZAvGP%YTTXyErmsTiF6!yU!}i|T zh?BZ3Pu-*J@9BHo!gEcYrP}Qd?5FPFI=i0^$+=)yY~nAN^aK66Bejm@15bz+RuAFv zDJ^D0Gzm0J#^pjvNDMg6AC8#t0IiDOY!VZx{{LVpibxc+A~m_boKlzAHbS-7`7DVN zRK)nChzC+$hs%c+<@1b9?C$vHh#bCLZ05*?$h3zd#|?JDJ+%_2QLDT#Tux4you)eI zSzgF)ttM0T7b@o5pDIyyN58%y@E?4UN|>!CI`8Pyx8y-x41BNfT?y=Pbb}rvEbuqc zD`5Fnot!_xzu0Dh_?&t<+t^M6$Q!=B$Pk3+BjQKm-^@j65YQ6RCSoDZ_Ut>3(}(m@ zvFmy!nBAT~ih}(AP?35U%Myw_e#(4EJsa!p``iv4pPV$ZQmNpH8@8B6DhGgZc|?X! zgDfrlfE3X;Gslh=$vOY%=q`bTRy=r7JB3KXk1F`(nE1~VO7e^~^g0=a!-NaJKUp;c zU%OR-OAL`ox4*BR*cMSfQOxhFooI&gYUd2as_5u?8Tsbkm2PC+&j9#M zXim=AOkJaVt1DTtCF5-LkGblSV#O4knXfgt3yMps* zrOTT6Q27sH!*!y(W0yT)ri>vGn;TtUd2CqDjwFlC#>luZMoL&BbXW0sy8(vJ+x+o{ zfrA+^YU_#arRQAC2*19ZZ-dlwFXu`V%GxWjDs!f-*|yZBQah#eVq0Dv@+~>568Huy z*3w)K7pL@|-VfDB%bjgeC=x=Z|L1m+PovCkLY|H5kO&`DR8pZiERxX4Dw>AEclwqq zI6fQG0e7swslMGIHGdqwm!S_46XF(}+E}-t8beZX->~{gs40TIRM5;@8(&Z3xZQ`gpiORc6W!Sl*x zjtt&No*mA*|742+%NQ-@G*UupF0$d53WG&tWtCa)T7K?ZbpeYW>_pQs||X3;32aE_D+)StSV|=@Day zn=oCSr*XrQVx52^KBD4ft6eZ|nAO%kmbayLoujfU+O1H+_>K6O*PB}cD@EQ#A@-cj zJ|%pQ&rG>#j&a9?k~lvcXGcbDY7#u^7`{WS(1vxZAocpB+hOpUR|>^VeUdzw1-UI} zJi(*_1mwP$1FNjH>MeHU4@fDpN7vg-c*X=ddtJc8ud&TLWRb)TzCE{GI)~4Ptf;}o z0w4DO)c?sd3_wDeMGvX#-+qUUhxjKCvR_MWSpfLArFH-k z2oB3*)Der3jx^wyWTXp5D|gJ+0tKG0G7fS5$-+AqdX-!w?2=arKcj2RkmIa%3i^{i zahsPs!jb$;f-u}pm-=L>o8Q2cA)g!QVEL)PoP1~Q)kWgu=0zR9tVZ`X7{RSST zE$MLatu!R`BEuQ_zQQv`B>7jFPOl$i4L1PT)VgCfH@eeEf_%eLYYgt2Qcpn@%PD#2NefVAXEHKUY0xWMZL+!WZnQiR-9er|U{ELhhb>eP#lV8XNK0`uGu z=bDR(*@t4T+Puj6sv|Xu!XNUVZv(4CLy@+MOGPdf=z|afn%8)Wi=?^;U$puA!=s|= zPI7~sw{q`==!jq9g92seLx9uArS!IgUtPLdT3h6o3aJ+c44VIz6#gzHaD!UR`V^lP zavm0yZ+P;V1XapPeIvLZ+v41}?#MDs=39hCq~>xXmpiPxCRs)^-71IC655RU^H}Vn zPNoNUDoOGBK|r%ZxQ7~WT}iiv;7@UuM5R6xaeW<#Wq?z=lGr^=qE&tRfWN~0j|7(A z)Mqs9zH?$BaeHyncdrwieBsE0q+dBZZe7X2O5w*aAr81ka#c9M$7mB)t&IB=@SYG` zNRAsXCd;2_uUA=A!`;cAZu3o|sP1GhH#7-Si)sr^0^7n)bw?TVcCs0T23(p7PjwHj zl1`={i^OqkDMeDxejU=ax70Z-ETArmS8ekxDz|e_m=slH&fde zBD%aE0MFcjSfmTdg6AgchVO4_{h?9(%3DJH8bHI~mmh0Pl<*32_3)Kd|Gq*4+*%kv8g)3`B$)o=ZT(u^g3V<3fB_-dpa=@s8oAG%7L|RiQWUQ{xh6C z9SW!FCLX3oUEm9`BvXnAUTqCGQKrKsa+>(RZ{4V0Cj5htj-8YTTxR2C1DB>KQqSOb zjAxMknv+`!Ra2n4NmDs=tTDwx?%8pt+c@?eBvSYM#-JeYfw1edHQ~!x1x})lx{TCz z5Czv{ZQO~s*W#nK{!I7#f^Q6;&z#W3 zc{JSN#!eoZE8^2(X!$x?-!G_~XGnn5+-ZW zBj|l^`Iwh-b{?FtW-N` zf`4xZ1D{{M?O0LSE=V|tTw8vPem^UUEht&9S6y z5T`n_Z*$F4uPx@Ig7KrQeX?q&=tMF){NZEWXn?QcF^unUNZ{aDdi0uKK~ zxy(H0?9i}AIM)1Fh(e&o`-JXCug%GEl59a>|M!X0#+7~PNz+&n)A%ylqiBq$~d#J1}-A&{-IRxaI;;sv`-6uN;0 z-x-x-2gyfl#=r-J`?uF%KT60z6{|f?PhP_z;tRbHI-cRHeuV=0qK#oFlUp+JF=9eK z%q21LA7{#ar2G1f&+S+eb1&-6_MIPI9ia(G4-5WuAui-DD9HS}T@Ly8S5?8=vny2&M`5j&vQTX?9@7- zHu8AZUAoCdCt0dfm+%+(f@Na@2WGl9x#rJS(QwXI`#~yn8645CrwHh1gR@2lZm0L} z_EcmAy&-YD-QsSeHR}BLE5@+wBXvZ6Jq9fXy)1C7TVXIW`zEuMTZhy)QywyLnQpbe zA`tk?87&=2xNmk24m0o#x%>;-ZGkzr`+sIB_f7-(Yw4}GOlGZgb@pE;g9?q|T>sxh z>PNZGrrs?|HovSGNK`}fDerv50!V3MBL`c~Eip1B1RC<2^~%K;qbH7KW!-)anXWCR zVoW&dt|yWkTuuFO&O8}RRmsTUn(F4P+pZ>>9_UhIwU&W7wrIr2Cv z!8BIGn2k`D7*nt${Y)Y#ARp3?kZetWJAJ=2wfq2=4LsY6_~DVkr0mC$`6kxFC_kl} zvfXVMuti!)T7~m=Fn<9hPH(iJ-0PIX!t)%O)Xb=yp1647Z(k51YJnM)2tjbC4^3V~MI9Ro8)*@pz;HY+X?ei&UQ&lp;v5zs-@+41h`NEF2YbA$VJ zid6t|d-4(R?%$Zawg`H{90&<__A?Y>S=^a^eOjo=_*v z`jj*F2chWLmhm0eHWe`@^j37H=ogke-o4yEu%bvER;v>t7kR@Wpji$P&VI@G(v=q| zjn88I9RXeuFnlJ6%#}zC3XcCt5vx3*(QWJo&S{~Qg~_v%noY`Xf9m`nIfdUN8WY>dIIQgxX~bOo-wPPUFjP-<5j7mMa%)x#aI9ZMNc= zSHWxD$K)7$#EY7}ZBYhYbC|qcayy#wG7Ny0PhML0hu|IzY~t_;%-n4sa99 z4e)@K>XYo;?RbY>U`a5g_B)m?8{RGW zc?PS=2*ayzR(}C>Eqa$@9GB~-A;L4KGpv zEt;EGW}V6?y;v@Rca>Sac4Ml8f99;dulrf(_yoY5ty_u zB^y1HsbJtw7|dk}W9kTLRyLhkz$DCe)LYE6<>yVd)s^c8Am2jn)}!{H#NWRNZVnQj zlo-}Z*PG1uCS%%@hY_>s|2*w*HP?)55w+M6*>HxBZ+v0aV41#De1EzbR(Qie>nr=A zkvbP#9crl2BOj0gi@n~1H8{1BcygZs{W46=TCGw&s9;zyx0kRh184tzT)c`3bt~a6 zVbfQ8d{N!W(ruwic}Qk8)zz9c$j75bxjP|@5sF&E&uGuty z&oL&J_fBw@TWQ1;o~-R{oN-YfadW0QOLNcu(Dl;{hQ?k0+RF*jiZ~8VVD%r1sN{Gx ze>S!FaxMT-eCN4u)Ng>b(QfLzJ*=>1cKxkJS`S!ESP9I=dOW%nn_s^L!92rGW6Vda zQ+0CU0*-Y*HewJ>*?=j9$48e3R>#P03q>nzp4EEOZT;$xE{!zK+26B0Goxb_s4NEd ztM<9{zx0p$r*C zG#~NDs}lAlNgXimy2ni}8Y^QMqkBkZ=}#cSXw$-1yCz zGf&I-ej!=ux`5ea4pOE(a7;IPxsU{AYi;4arqA;MWy1`TT|?c}75VHp$sBzd@{~aJ zRa2nl;vO;R?YW6x$&nRq{beyU%!F5BYkD0aCxw;vE$HjdE?3FLQ>dh(8_MDVCI$bt z;7OX!Us-4%^je0pzUb@7rFgn5yMlWT@9AjYzv;s98-5{mk2nRypc8m60XL^3`8aOJ ziNKi)IV)&H`n!E-zrp3Lts3#z@gh6JfE;Ep%@vVkw(FceC%!Z7J;EGa4|p-(zKt2R z1{I*aWG-2Jle~4tf2Ob?fSwR1Owu1+&pp!ZEC7nv&(uOJKW=UCpP%iakr)rl_w^$F zYr;p!hm{CK>Hv5PKbj=yr-iYDCQr|?iA+Ehd{N5`C4$_T>;nJmvwzRBUoNlkzCm6o zCtqH0kuD?#Yj_jnApRMy;BzH`X7BU%w;E{5NkUI1&_BCQ^bzuw(GO*}_O}*touAKw zyf2U7k~lbIQy!bQg%`;3d1=+njm_N+#0gokjPPIG?D`i>HqAC}p2gj=L0YIjRl3HK1>^3terFmyjM4l4PVqS z+=KkN;Cu%zmC^jt4Y#CtKJghgM`3+$N%`fCjxmSv^(Hulz%EX2?i`cNGosILJfT;N zwMsaz#sMhM(eYYx{lB|OzV>~7jZ28nAJ1y|jMcJc;l%*pqdi-CK%bWYy?z{gcKFmC z0b_36NZnA3n7d+{@$sZ4V8(u)3BH*b>7@RrbI#Vw0(`Gv3+`tDyR2HJz;}VW<4D68vj#;^7gnp+cEeCY9@79jr`@MbAG37j6bm9fpe zx?HJXm_HP-ATH==w&=bpqm92QxO3Qw&k_jCn4`)I42U)Ak^^t@Lxbm%-1&UvqV0Lx zWZuwN@&-w41kH`paj-lJwAGtpU6rz>RMY+Z4{zUNyt@UaXAVv`(FGhDx9tDX1wPB? zBq7hTG^A>N>CeN8^J)NM!B}EQUAg7G4^{jpb6q|jb8(R`W14bD$y@MycgII<*&T`Nr38KSqj^r2P%hRuJn@D)4Az`ctN z3r~JMgD$S&=xPkY3A;P`Ha01H2w3wzj}6+aTLOF&KFNTj$)=kE4w_~qPiUlW-yZs8 zXG%;2(-riG(Q_D%neMv18M$S&2-Jc_v}NV6aMoye}q7~D~)JOMWrKOk-+qT+?< zx;Lpm^~kXjrJR~S_|PPlQIk!7llg&5hr03@ut?bv1&mQGdQXAYA&fouhf*C-8Fi=(<{ds zXXpQnBDV9aY~-<)AM+sFiC8uAE$b#MCNS}TWXyrHSrDY4Cv9U^i_@BjL^vIGY^?$! z1gMEyy`Wo*3;FoV#H)V)J;62Y&9eB*N?RteB6A-`qT|B9M?T69;K!FkD-)j%JgOi2`V1K6;Ttf z@-*?)NRjE-fHK11Og9-|ZcqPH*V)pH^_@$~0dd16{$hz8Md>zdqC!5U+g^xh=%{sV zU^^6w5c|XEtqL~70}92@b_vI>&J+)IsJhDiZ8=M>k&O(xnewVC296I@BHQ7x%>P!= zMBF`YNsz9djH8paLGu99(9gp6wj+NC_=k;4fho#K{QkHcuH~lfh|6IB)w6hJ9{oF8nC!s4^E$UCs3rLzoui4h?R$$>AhvF?6T0}}h zRX`C*7JZXsq$WGd-8#!JH~cm${()t-HJw$Yk_#zwlw`{dsZ^hEi98Q}E3~~laauiy z28u;px@hrc(-q$I!d%*&4&AX5YR8g*0#O3m;Qb0L9$o9e4VD+eZGOF?b$oXG4)l01 zJa6Kmc`0$VV;!gB)_3 z%zuUehMj(KjDdFJesv)|-WNkS(Li6H(q4qMvSWAj8T$r&0fng1+_m#@$z9t z-KLB4Sw5(8N~8r)-2$PDb>n_XCQl}8$hn3wSB({$eI_TVA=vFz5(CbF*6PKR{@)g! zE@B8hD;H;;W2^LGkSmsZl{=I>u(C$6r!-hrMV{iqlqxXA2hv>uX8!|pNOvGZ=(7S! zzi-m$DginL|I$KLT8wMPD^u zJwEBv3pt+u`QxW2ZWx#*4}c=2o&gX#lHOdzeoFoO`)aL(1QhPdM5c|v-ii5VOPmpC zV`RuROEb+}f@Gkeklu#&tX5MbfGGtzLtGw_NV7yzy4&=t7DQ(u9zKs#>0*aPQlN3& zl8RkV4Lut=FMCnp!vXwwDmC`cV29Cdxe(w$HBNo;1D_UIZ2O}$#@m9$Tw$;k0ZfRO zZvzU&lrH1D{l_bTmR_=U`)A_dQaMZG8-iM0F z0RkO-Q5%5}c#+ni0SVghyOdy zZhCTxO2io?ypx8l&V#O^KV<%|CJGrfF8F7;@W5anisv3Va7HBw;$-+Y+!Ai|KL89O zivc`pCcgHAs+Jmm#Lwy!i%y*hbPO##m}Qr1>bqRO{!|l`1#Uao@d`j0D|!)(oUe!C zQbjLR&_+c7a6K`3yYosF0~|GUL|MgA0l=i~r)-fZT5!Jf5;^%6|5#4CjuvHWqRQ5n zykcr+1*V#F>W*w#c?HUm6Z1#NKxaiPT*!Q;-@4+PF@L1;ggd@gaMjmGqy;h452QgI zC_L}90W)*vXSV%#P-a{!%%WKh{fwp-KK@v#tKLF&gW$e{U2zG5hM#>{HQ}m6^qG;R z;E$Dh!v6UoZ2)BVt-ocF@WYir&b~>$5hNJDl-G&d?pUUP=u_@yJw78Roy&fcWT(Wf z`TeGUknBFRn%6j(q zQY3#!K&EdsUat>9f(6d>$pANJ??1B=|7!Zfu3NNqK;pWlH&7HEQT3*ZFTjp|!NHEB zSzNEb!{`q;pk4@!ttwQ%uodNU-$QUGZ_KKWl3P^x&BCuy=)%h9xJDkQ|93IF z-Xm*%p0nRv8A7Fzsm%?1R03``wgzh38NXbm>~@JECJz0qg)O@VF!fg+=Re&}h|>2Z zev@>4Bq2n`T8lggGF{KKo<<#|8fD+&>JM26vlRw=mdW7h%5TW5bXw+E;5M^1nlaUfvkM$9$`G#=7^=e9(4xAc?zE z`&*GWEm$cjW*knPh)R{RoQ?vSd9~t$WJ^M4zbQ|so?d$Uyx=`#nXnbz8JU>|8PvG9Ac_J2g-ZP)j zJ!?=P6+eC1Ks-}wn)`<<+unM&oDw~;6d)UtH@k=;?yii9ETK_kQSHo+x zUB4`Q=IH^ee(oYntUxlhST0YU0O+@JU{0-7lUF1b3XJ5+k7^ZOmfd>zJrD53ZDin}AS?SNgLSuwy~zDFFJ(l{*mE#h-@G$&DSM8tAT*i=;6UjpmPd3hPA033ojlnD`VZ*nqY z!OO-jj=CbpX7ZZHDv%D9{vpl%zY%6=6!Pq@+Ui@!W+(sPka>0bo2|2ab7x`&ekaGl z+2Yg3jKn#&L`^$E%*jaVic0m9D$>0L2nz==!_AoZwO_J4P-i(c@aek(l8+(O+Y314 zr9MZT5xxX9qW7?wH@$r8^V~LW0?(fQP=(MgkEX)&=4|7k&?B}8a->RP$dH<7D9nv& z1D}TCMZN54fZd`V+dPiorf-NA2w75Bw6E8nPTr(Q8HX^raKi!K^5%Clk1TbX3|nV) zodGa)R%tB45KWQitsg_;!lW(T8$u)0(!0IiK+p7VP_@eeB&z!#i6WpQyLabi9F{&m4m`EMqjE}0H# zZ<>yWBF?ajrT=hWy{0OiVTO^W0c7`^K_B}=aK_I(iH~|a8uvd6n&?e|TvY2Qt!laK zRJHS|+pnXhSxP7%~Oi%3*WZm4nAB#zXOo>0IRu;7wIBUm(zJl^~J6@{}K_NYt!gR&T!L9Z z=B-@;J0Z~W%NypmH>|}Al=~Qe7}Kg{b-Ok1!2DBo#LDfbf=b5MBzFLlWZP#}{5AA8 zxsveH;)s&Xx*ru{TxLu}CjW)Vt2k7ko#1x!uKC$*IvlKyMqXyn4)!s}YnJJal^l+4 zeBJG z%6UdX5M{^T1S`A{tA+2j95D4knNA4M5z=|pf@F`!)(XgOh*0{37?*GB!=Pla?tEQ{ zV(N&S8TI;$+k4daG*65?R%|lE(ke{%>4Q=s4agmqgb$MFlh~q3k}T8HxjQ62;BcD!t*ql8(iO^ zG;6mLdX5b!D7fbjJslJg{~+|Op5MQ9nf!o~#t$vEp?PIY=;&Zd7!B_6Q}pJ%QuROs{$s24!wUhIkRB% zYrHRX>C}@FuW=IxOLj^MP}4iT?>PU424pL!EO>jfsGh%1?7TavlzJ-&KBRkpppC(o zs}(e{#a*zernP|b!0qu0$CL)jSxI!t|)QN|}qu4N3FF~JTL2t(;c&6U9$` z*ZKnM#IqRM8}Ipr6Rc&BL&*gGys&q11_p+qNpUnjzu^7zeXb3?!o!>57$ztz-S81u zcQjp`Mjt#Q2Y#8_b<G*1_p)NDcLg0ubO%Y1# zN5djI7&_2uf-u5c?P4&Zywf(IeRRRK%ExgBZQyH+$+rj5u}jgXu>g1mq=Sk|C&^xl z5)9==ew$J-aihGIGx2|yEB_a^q#G4T7<_SLlmks=okD>!*18)otw08r+yisH^*UD6 zw5^U4SdApcrPTT$WBaSohOfUxi^7Q(Zs;exBp`EE|!}QmNe=U@K!)i=W5Cr zRPJi7|6$j{2V>9!Av+DAQ1}Lk4M=b*IBTi7O#iPhwr;m-wydp8zsBnrxC34qCm9e# zX${t6M$+|d?;BhrqfR+7-9HX1*mRprdtZdm)quU&%R@BA7B}QrAmXrxSSa2-T#@`2 zC*lKV8PzuKSnK29ep8dS_SEo7b^{aIS;2BKLRoW&Lc0-s>He#fF>vw%9HP%I~ zrE{_hhW2{?U;z-$5U%8uC7xfIn|7crPB{Bbg=u%6y~^inanfHFNRMgw+Z;^yeFK z1~&g|AUNkmf{yffQrL6Pr`T^f0gQN;)>p0IapnQzb6B11WQ0e!TA5yXg*OQ9ExuVb=dI`O`MWhtx z5f91kIJ=IXEl6aK;|6y)@90&+Eq?3{a=A@wKmn~_@FJl-SG>^Hs?_Yt%q^`?X^b`P z-#yCj>&zgIo;}>GlfeI0V-6XU-)7xPjGun8{}PmXt`hM^$_$_4R(cTA^qpFx#)+ht z8BtlvKl#GU0U;Sei8TobAy*ozpGvvQskl&D+jjs#MPgEJFw+3L)lMkTvVZLq=nuOw z=l@aA+h>`r+vtNHO~PPEj~zo@<#{YiTt2yi9N$WP0-|6;r$ z)9HBSoPEmD(Z|{jfw@>i5X5|p40F@^V$&NO;~=Re&kB;TdlYU_)&d;aXBjGo7=MBJ zCHV%rr?fa>bQ059Zh3QlyM%26So8{nKrvmHx5r#vXLGdCsamFvpVr}ySO#&SK`lE2 zriU8n9fTdz0&`ZnPbgYE?clySuOUhO=MzfQ#J4XZYKa zwBFjkeGraXH5{bZ--rI8nslp7(HZu6!<*7W2LnMO&?(_1GcE!v2$-T0X+n4H!;49;$gu&d(3P z??SZA&e2C4tPz^Zc(ZxErG(@aX0g^r1C+5PP9j7(wZ4_M!TIphS?CE9`G}cG4jBUY zsIM}`Dj1-LIV4T@QpU{T#ED!!q z0MHdL>I5_wjNI1Ig&F$eyYGoJ%w0HJEWS3->2Ehbi$!7t$ofas|OaP?k zlEw;Dx#8+ubNOp(>H&}dJbeBKTW+7pb+`cJV|JZ=jC0TaVClQmX=nV|d8n|UlIRBf zr8o?Cgh_49ngGpOTETWoB~&Op5x` zi=y_@mo(sa?)J~JedU`Cr7!XhG7}SNz>y0;9_93t-`EJe7yo*R{;8v7>AT+oGH@6;hW@4z zEnknon-P|+EoE^4_c}fZsU8W(nl6gQA7KXfkkY8%rVVPhih*@?yG%U=!!Sb@Fic+s zDCAU~rNT-de9DifOuDXe#v={TNlVt{`)(^3Q{3c3DvgNFLrrt>(-f0Ek?;xBoS881K&p?vNU;d!#=awCo6{N}jBf4|DrV*`q{I zNz{yvfnS3V1UIMv+p_L34|Im5zYFZDIjQy<1mQ4ub47TydZ4lyK-0F}5nQDTto+$0Z2I!)UlD7*?ntJOw$t%j)Dpap6)ZVl)1zN|a2 zX?aVShFQThRMIt=goDo2ynO-^hVy|y^E>%o0QOyc%EsC|_tPJ2O6>!epRxY=H2CI? zcYk8g;Y6hgHuG8ze@??P0tEpujj#|(bthPPdZMOa)MW4tqC28)^A56hesz$MSFF>R zbqDqiEf2r22$ZT=9raqo3fp_4b*BU@-kN`0U5;wzgu? zwcYQ1eg#u5EJ4uBlA;@9ZsRu68=eVeP@+YgP||zCwPa~juGcJ6gV%)U*aS>YeIojE z!1;3WodBGE{3~m|JNxHPEQ+6-W9;QsTqe3PqxWxKlg-RqtwSet9yu8^Qm>0*?VD;oqz_N;PhR&ZCpC zWasCRaMm5Xfu2jRpjm8Bq0Zj(%Zy(*KBiM2Y`Xk2HXOPw`t!ia8S;eyP$d7>+yB^X zIuytg+wjD|b&Mx`x(apiwpH1X+GSqi0-T0ziSg zY#G1c^0$obj|uyq@RI)6dPV!Y$Fs4kHG0JBmZ)W^d-*=nrCb|*kHuRmn2A4uW zd}BM&4N**7$GanX;4rLB;l{}MI^-zg-@q>ek^Ya72Ryn2M9O1n7G9}v#Bjc5X} zjg0>3Z)}F0i*H`z*bmP!AZ48BhL>0H?NAv##?KV}0pWbxh#~+qFvra|?{M$KzZiOS z5`3olvU>mMlgasZJieU9zeP=qU$RZ~2ZZx&ldA$iSQd(n1VSJ90tKj7V^JZg98A^O9?`S$rL0zlJfQ;?7P?k8Pb2LI^+sJyTyHat8c zx^d-oTqe1~zj190nz2;$hlBI&lj8!g|MHK5;Y+5`uDvo!;oR`dsh^L>yb0zfnCQr~^5 zp4=lkG`1YrA#A8`EsD;&A~Gn-lW zTb^;}s~Ufz8~j>TV@-dPmhTk(q2PQ!e31Z9+y1?e|6%Bk*+@RKL3BgPkC156K%dm_ zKY3k>=nn+v`{IiPfJX0Wu`Z51$ni6#px*3OaG&BKx>4mPJo=YJP*fBf=u_;6f%E;5 zZ2>rX?-k4GUw`R5%8#xC-`GmncJ3xFy?xEb@rzhkMReoJO=xOvyMA`CY-oC5zw$6 z5|?Zh{XyV-pJ*%qG;jw+{E2gKo+Er=Wo8KB3o5h7|KeNQ;hE$mx?$!9jw2i;Gx63) zGjbJEYNv;ZLZmTF8(5)4XFrr~)EFBM-x2*m;C!EGBmmn^{D6m_z-HY2-Xs2G{3dlw zWYchK3LR(V?}4Z;38Fs)obMNn1b~L`y7cQCczox9KBv)6FmGbY-1_VoKVe$d8rGg( zXx^b4mhL$F)qY@2*?jbY!t$154@CPcoUf0@Re;rpFQfLtW(b>68P%57LF+A@P=0s;MKx{mE2Nh;lRY>sZG^| zlaQ`Uy%SFUL#+VpIQ5Wa`cZp7W%uoWaSaPDZ9|XcW6^egKg90nfy#>`;X2t>bi>Ro zELvJ*Dgey*lWIWMNf+AY+R(Mrh1C$x&mvIG7*1upR0@EHPpHb0IDM&1uO7)qB}Tga zI$M7y{8rL!&tCndP(o*RF8O73`|dmYn62M@{Htu+f%8w;@}LE$M1PPuIV=GCFF(W0 z|Ni2m_sU_`&@9vXzs=ZE&~w*=wwbmJT?bv}2}t)T=4Y%V0NUC*n1ALcv>LlFO9CM8 z>St!u>fHQ{wxwTQdEgFS{Q6eqzTIaW75zcxKGGMH4lKu>pDv4Th@yD_jmYy zvSh>=8GB~O9=Y-i>kr*iEdZ0b0OVIP4FWFRbCw1D`X(nM<-vW_UmDGfA!1QgHu8_( zbbrweGqBqRTDJ;C*;1*I2{g$6W(ut=SzxNT^^c*QOepLcMY&rHAzsb4hgfuya z+WOPK2F*XkwmtdzO_l_MUKA*#mwa7b{zZ{}bpk-I^sNY70P;T?r2-#+@S3#>j5|I1 zyJ`EEhdKbM^8l!c&pf~xcD{aS5Yth?;L}s1L5zaiFU4orF`02u8$Bi4s4Knm5~2{5i|0t>8D`)&6ZqaEdbQKH%>5o%HX4WPMLslla&*8h|W_#zuz{3J4)SMy7v|q@43m+ch?=dC+jCb>lB=m-aB-IoZ* z((&nY`srMYci+VFeYe>;*QMTLpM#*~O=;JmYpg%~`8t$vB;8l+hnSOnvNa;mj131- zrb7ex#74lUYk7F}424JElJFQD2=`(Ba32x?k3oU(7!bt9yz}f+27axpA-G{9BrcYW zezQe*fTpcEfPU+zFW86y)0QB9+zhlEIu1<|2BChp-e}abKbrO)jOhNu*_d}7 z|2GLU)*e)OuEBezif-7N;5N`7cBRX}#@iQRHR_{j+wR#m{%*ZTW9@7l*q{MIo3}vawy~(tvK1-~Z7gbs zBgxD?RaiA<*zDEpGjB+}g<+GHphf$>Xdat25g@T>9-DxEqh?|ap8%92GI>S-2&z^r z-*W*g_g%*3WA~M|4PChabyqdcb>k;*#IIF#HgnJ9mAjQb_rgub(Y60Lw2T{;<_+{@ zf*^yu1i|Q|V+SHG;eVL5T6I;3!^v&(lmKK#>W$|({Q7S08vg`0_{Y>>-pI`LsTqF0 zReLXE^1`j?Jz^T-2PDeqHEb%z&)vw~eNLVuUkLz>O1${;p4@TyC%M3Fln;E{R7L3~ zO)+=NanZj&hm+IfD*+%jAHRp{$&FZ(qi63ja3AK!0)?J^OT(vA1bkapgMYJHLVdj| zyn2>}$4LK7vlf}LkM@Q~|6tavNllgkjq0*EM70i`k+f#N=-->e`5K5W05tGO%Jt_s zbn^w9Wq9v}r^O&-74| z6e*;^;^7>dsc}hZ-a6jJZ~c8eb)NH{bKcA5sSn4`5175&#>DwL2HndT-*f)?cf|A^ z+x!liN0wynLeub~9LOmq@`~`D7d!JGAvXZ$)twwC78sHnx{c^snAVN{3Q0PH6| zRBu^>&gG)ixNgNpE)c`047mX;I=mP?{rqNMT+U_nSja_U7*!!R0N3?B&R+dN6NNQx zTEtZ)BcjrX^3EZ0p%_L*NDV-|0Eh-7mes1D-Ct|fqH(tmy&FrI*>}lEfm$qvQ4KN! zaCmRwd3uqp$G>}{kLu8&!rp+KF*Bw%-6a3YFsedg0Ak>%*!f!z27c9M+*DnLX}gD9 zG=@`A9D+L9K0uTrh@FiI5tAsOEF~pO80K98hYjfzF%=eRhg0 zyfI{@$i9IEHO;a#m|7r)QJIh*0h*R45#6pwY-0i8W)$jIw)_VS`wd%cn z_StxyC>13c6huNq004j@`&Cj60Dyx03I%`%LVg&ylv@D+#y@2x#WcKfPJhB0Xvh-{ zcIGWqY1c0Fp^D1>z?MQjJwNXm+>9o{r;DchN*^7?#BEP$7V`_9A$n~MN_fNDddVHn zgZ>9JZ~sND@BQ5Q(v9GaQck8|N5cB22#M3~M}QJ-df~?Tmd)`BVrfiOf6q8Ne~nKD zR-MxAu4)?^4Xaq5k{}Eu2(5tu#~Cb}q43TFsdt5(u@E8vt)?BgbXXyOFL-^?eYf;5FDjW2 zLbo_-`i&z4%I3F?dE|*fn7gTJg5Tx?>zPhbqCb${xWq4$i(yzC-k zh$?Ov&aVWeQj98x^cg7(NLBfnjz>mJp;P*<#URrb5VUVa(EY1;3Yx7PqT2)TghiBUK)-vaKw+<~5>Ikm&K zV+*;p!1@S!TzfRk*OxtykAEWEP=~7%{BB*Ui7Z#|W{J=DZra2|WbW`EL3n3Yf1$Of-Lj|b z?M2GRfq9~SBukLkuqSXNDDSQ&m_HMUG3FkxV<8@hDyNE!MKGT_p-NYxI9-K3 z<@1-hy~tMo_|Wn(FH&mModi47e%mt5Wgt(*tcjBj z**7#$P@trZck7GBsRs$%it6lUy$zGNvNOk5G>E^uvAcH;R7cBd6jog+ajPco(rwLr z9x&;ai|LTz@FJ$+xsZuh@x|6TW_#RVm@}ivCo3}eJ-E}J!eZXmTt9tK$kCKREzIhm zzHc5f%ft*Tz8W&HKQ$&Vzp&?U zm}$lyQ0B=?#XbkcL~CQZEv^5-I26Ko6rR@uNdi37w>XO}FOhCuWbCRzrfUTML`~_) zs(?g8CC|VG#j!Gz!B^zlj=XtT`rAowS=Nk_N^WzPr+Qtb|n6Y$r=e1k9ugWp&>RYj1 z2`y+p^hnuEu5a_1gw+gB6EzfY_ZlY(H_W}q=la96+)^8MV(OsN?2tdQEh^D5qH|=I z&5V^H_!~=4amxB-;jA(Q#rKJ7Q0;$o8gC5h`u&l^C#!~FzVR0`&NCAag|_$GA{L@C zNjAzZGobXS&@s%BsK5#cmQmPbhV;c-%KUR>Bfs463FH zM}7%;fNxY!`h+-nW>A6&a8x6^hk5Hyh;QrPL$RNm=R}mxcmJV&947<~D6hR>yicpN zqcBGT8>r*i`uVQDUtkMrt_g#rceqS><>K}p!^M}@yeynEkiQ_#LcJFny|QNrO%aQs z{=(pF{B;QufZ=c_lW}W_PG(zCkE(StuPThOn-5^e~baj z@7FC9mtq8y@PEx%Q_63?Z08cUYQ`8dX+y^ulg@VnU*5$> z#$1X%?k^!8pcn}ek=lA=_n?qRVEJ8hZY~}0;^h$ zH~SA9y};KYcG4R~>15mbexC|2{`?(c*|@xXdf_BXC*4GF%C6?*-1zN786J@Zy%-Zw zubr5Po^Ut1((C2LhX3#iXXTHGh#jnZ0Ww)?g(sY=j2utadu0W{F3T1M>k5Sy4#HS5 zcC;)NmfGtoINQDN{P{x6I${6&usd(j3HrY+L9ct#`3X3J08<{(qp@aM0^#){JTi-+ zj(`gsf%VGGD!a90Z8FP~b3yOX`CkZ%Lb0fVq%l?LX^n7RDFi)l%}AM#H@m|jf+aU~ zJ89+jJjk%qL_aRE23Q6v?deaO9IN^O0qDnz2x2iq{o_?URWhutOd%B>QT_;N2-8EQ zu$Kbp)X$D|G^+p?)?0i=>I%BDTH)a|!4=_fn3fX7^^;yK;y1KT7A!*H``VJYgA=pkOfd|MeWMO zc-OEczA!X26y{GPU##_m8M^N|D=K_2Ek?NGmH6sj^5gXt30SC%Qh8W#3??UUZYU4- zEzp!jYD=E&;*EvItv0t33TBdqpK8$@(aO8Unr6yMP18chWa(6IqYQol zt)ve%lKBIlN#>mCV{mwU$%Wr=y8K^*Ni($p`Z@l6>t9^|{!gU|nXOboSYYls=D?7P5Fv9i?$V@kx1?X#1bJ4JZjr z6qBpSG=;~S*As@wjX_qj@XURQ(<4hA=OrC8KvZ8Vu?{}%MXp6oCkPj>un42wRzUo~ zLzCf6{UkzV3x?`u-}E$hPFg1*urq?TV948ER<%flRPw^J2gx+`0Ugvb zi?&bgFtR=oai|hbeh&;`IiRD%7Q4)(xNk;V#(EcjqXBBr8TIRlQ6lG-#6|&LVcL!x z+r6&`muD(iV)wt233>(q`k9YWiAz62&2xKN9S^9tmH%?raeudK{9B}5yLeZ)jYhCD z+M4G~eGdCYdd-in!X&kH()jZU3!>^A!WN-0#=S2E_V02V_svrw+@~pa&3u|pt)>li z3icvOLY&M)!p_&rFq~h9AbvcYpEc{=Q3t_6$x*Whk!_EG_VPm|HfD|%&w3`1*b*8BFB0s>w6JmIVp_R#@VI+0axn((<1L(q!wNfbc2xB^*JF4zTIOE zQT&cB3I4#P;Y7@xrm_Y{N>e>8@2kfuo!IFW0s?;bExx|6+newT%YCnHivk8r3BqW+ zGxXz61b&R6k@Oj&h~<-#U?rb^6pbIgv*Vw;nb!PLR{kUNOc^rO(k54w{Q?!i#9yp( zukGW`{8{Q1?g0Bvf{vl!s+^j2MHp?Akh354&Cvp(tgQjf+sVEzh zNqo1VwDDFB74X#h4!9>Az(O%0qKRWoCJ>z*T|NXU5@pq7{im+wRcl5H%cd4q&JdCu zAhRJfO)veG{#Oy=YVpu2v4^3lKxJ`>+hZSen14h&={E3E!1ZmAqlB;Kc3;(_U)J?U z@kz_>4hDR?F#s?>OEmCf= zu^5N>(QW9ibLYxf_-WOcycdm`DTeI|Z+0}np{#l8J)F5o+os>711c-WA^Dgqh2|NB zPW7wO3EgMymQFvC9`y7&i=p4-;P{y)uLbIyjw_8Lz6u+$(Z&U-hP?vjRX~7kd4EFX zwLnR;uQ|3uak@BxmS&_0*3ZK~i^cO7@HFs~%wR6*b!#S%0d^~< z7VctTu4`Jv`49vTyB}a3&KlD1?u@86xnZgu%4{0bFL0@d?Qt8x?{S~u&vnoofG)>asD@zBgG;J$nb5{Y56JOL z-@HH61K(U1UV>z#ztBGbeB)?@Ez1cgJc=!BP$Ap+JVfQHYgK|;X^}!GdSPRTf6kLa zAbOy#Zt+QhVJ;=Df-JP*?i%RyGOfSFt?Dw~s*#g?e$e&$$@gsA(`bv>7BhwrQls~w zxMpi&50{yWXC^YF`F*OTo3-PXwV*?&s53Hw{aUBtK?}`$K99q8(qVo;EW5CQWbLt& zYQp`17C$hND-}vd&T^ePQZ@rv6=V#PsO|GpSKMlQfju8aHn~NC&XCSxzgp-t#yh)+ z`-@k+0Vu{P(csp$0?ahooOo-sI^8eNVkgLxG^YGY&SK&T+#qIPQG*fX`LyQuB{;y% z+OY14Sh|hOiifIdz_<`!3)2E$Be(c<(3?!NZThgZxYX(u8VMwmP-IXV& zS2AyB*kLXxst`Z(kBaxn`p(C`;XM+DFsbf?QAszuB?9`Pd>T?Wze zp#mqytWgnK)^mMH9DCCa_C`3Y-pYzO8#phG{wJOa$T5wQ!0Fk^#*!GBRz>cH~(0J z4iTIRx*rsyj`DpQ*~Jf5GaEEV&PRl_hC`4tn%M(>x_4fJN24~O4MD{8wT6m^!_9Bm z(U##Qp{d!r-<=kOYXbCOCQJyVMuqnv7|A`9U#|9?>*UBnV~(2O-mCXkmB7Da43$fR z&DYWuhdukmdhvwz9RX-EeL~ihr-x5Mi!1$W0%SfUCb7BXCdQo&>%b26&z&Kno!PP= z?#3pvlof?X%6zMqdb#gx5%xdY=(h6yR8Cb}1R-K-#W}LT<$FzPA6|LQ!T_k0-59fm zo7I2<7m;ervr!Eun>NBeI!#`Gw-^=VucoKM>`)8uDTIJ6uHU3t$QmKA2*&xPi6{CV z6D;JBT}6dZU)iu&F<6f^BMAUfD7ert&;%MVSrT(9mM!glj8e}W3T#WW+PAi;njhU0 zf!L5a`YxZbl%Z%L)Z>`g-&grKr(vfj#y9Dx(DzPVj4-2S_fALjVBEl6yoqmpmqK6}_5FiB~ zbB4iQn~sj)rp6lRD(~B8A74WLCZ3cif^)Ti{@0N~65+ES7G`(ii$3Bu50L@(pt)TB z)(E0aeG%qz==Z{gj=uop5ag>3XV1UupyAxCvFZy&CO}@7pG2@q*Zbwsmy`4#iI*hC zT?37|X)-KAf9prlbVU-X!9pKRZH{d6PqD_QO431JeyYC}Wa7IgQ2U-CA)N%@X|?X@ zQJ!GcSuy6-CmiR`9BBg5ULF|#Mx$^6v4gfQF>Odnheuv;2;W1Le(j`c7D=M5SJRFE5*v3Sy7F}p<*NxAl;uCik1^!l z6sv()S8hf89vPkFCo!aI4EByjQSDHEj{(wy!SXe!W~dCLA3^njvXjBl+hx)H0q=eP zmGV|Dr3Mc4u_K}Znf%O#w?c#Bg9EA6F%H>C zdzC`a`8x#qN_Bf3B&7!Ay5c{ByO(Tt{u<=Pk&lgl-+LMoG{DsP%E^iG+93luGl&q0 z8kj4?v>;`Xa;)Tw@++HHSGKqe$q}^RoPGkP5XM)M+TxR8m_rPkBNvM?EE=1mNBEiI zN-A`e0%>zDl_b;is;7-bhHim6_cYiK%AdG)#Pf@GgM$a$hMsVZJ;R%7*4 z{2v)dAl&yS;^ZieXrYmOnd%Z{CnZB~@e(MzMNk}*`fc6OraQ8p7djH!y69mC z3vb3HN{h@I>+?w)85#?9!NfFwzH$rO{wGwaGJ6vp2LQ3^5@`Um(id*T>7L+}7#L32 zjBJ!(;w-Aa^(Zt-6nS45vxbNbja;y>b{2a+`$Nb(!Dzo&S;_lPZpK;?v!sA`5sb)3`i2 z<0cUT+*{KUQ0d}s`9FauzVnj2hcQ*Tf1!UdxGqfhFi8Tvrf(VBbXO4VhdF$`d;U1; zNago0)hYp~rAM89#7QzR!B8+A$SLkP>nE$Eiol9je0tt`bM&Y@Ae#5{8@)q!dz?Ot zL&14ICEdT`!-R^#RD3`j#-(Tdpa0Z(f7eBR+K2sI`|E}dWrtq%r>GhQEy~NnMT~4q z?H|>z$s0elb*M5HiQ5_`r|G(WoVtEvp3``Yl|{*)Zk4tp`u?xZIMpQ&2pOi@K`SmE zH3zWlGaHBaci@*A;sb7*&*vh+n@0q}*>fpvmvW$=tjC$R zh#0leTjgYk6Ua7;w>36?(B|_(EiM#}xCMff{B@Kd5YS(@T!BG|tRis-C1t`ciT*IP zjo;mgcW<;Y`nUV!QBb3j!P~5^934u-u5=mjY&>h3>h2x=8853Pp+#+rO_dvrff1|k zPALII4|wb9^SHH9$vt|qJV@Gqt3=N4eE|;7+wy9JJ3q`HvVJ#+UdV)8H$$wG-qiO# zaYJX&6LqU5)wzt?q@Rd(Gj-v2lW`jA$94XZ)od_j3Z5XQJGUU{gFCF~&G?)bgWS*G$~zvZF39SR1poq+8VOJoA60>j z^Yf#RWCU|)r}YUo3ON^HZAD;idXuGMAm{`f=i;%a@~-HgnfNyMf(0UYFEMaINXpSB zM8I}X!`ET~;fr>Cf6^HZVoZNqJ{+#R*r zd{-RO2sEtXC%K* zxK~7RY7(>c)T)0poi*^YeO&_R{{eaWU|Kc5b=CZj)8T{hrqdYJ5=!mwI>eEcR2h;8 zc2>e)2Ddc9Vi|E-5)vJ1j0-Gl-A&?QdJcVcp02#V)_?Awj6kZ8vw{&3#CQE_+p_Dy z1-BW=Fa(?_^C6SPFup>yHn@HX);KdIbJYeJ*%Tr}B`xzjeYW!%TzOAY*_-AMq3?;~ zz55v6XBa+3BbLi5&So0fBD`y37-r}O&HItuUrwflXwUlD|AtguLS^UO;f@M*ho45z z50$tjevt~zy8pkwq#OH(zHY%5A~ANDFSZi+C}(BX*p7Zk7xhY*;Gq8!#awq9yWU2~ z2sZx1#b~&Y1_^il9gtwWCLqgKKa#oOH2Mu6iRMj=BWKp%|AQM>f%W;8G#F1q_t95l zw*-z!Mo6R4VeGF+-?Wg#Li)$|u9w$T#Qr$6?TZaq&*t9?mIG;6&lgeeUUd5{CBBB& zvOof*Wgk5Iu;_h|aacIYY%|Gj!uMA0o$IvHh9`hp_BIBR`zV{`!LUjjpz)D+iQvIV z=0B&wZ#MEx`0SLkH5?x#s2*=g47^_vTDxdX9w9YDdWrp zbM|Q&g96r5^G_->yAJ#4Uk&}$KbG$wE3cTn>jhzd^R3tW6&W40Zf+ueu^~+vH@32L z;3yXxNS>fvAJ5zst<+oa6Jft7E5bMwbv{RxTGnLQg-z_TkdNiDBLpIFGm5}V8e!gQ zv^kjWwfgljni{XQ=ercuG%T1y$IG_Q(w5*5IR#lc_XkFl&F;3|j$FS@3$xoGJQKu!KxmUDkx+R ze9;AM?fb5EJ)wKjxV(1`GwyZUvBA04$Ocia_wN-Bj=QP^uCH?aPAbm0GuD#e!G5{k zKQTbY?BgQY9m4X34l@2_CDBO)jw$m#w*3^wZ;a#yc4``N?C zmbE0u`xbbxE)w={BzEs{d9-P1jE9pVVx3=z(`y01#WENAMDNOt?4j9RY4cc5f#oP2 z?}%;oH+-X%qE!}bCmtV1Pc-tFcs)g|#woGQL!yGpwPI7$l1h=qRTUJ)y;f({MRJN) zt>N?9LJ}P`c@B@fZb{45>C83dJyxvn;twg+1L#v;R?hN%Y^^TcCRX&#>6C7jDinWy zE}k|0#xx&1fk<-bI1{n%Bc$Px978EsDe7CnoxK-931m+miDBU2C@|msH}Zu8hac{& zs6!9$Is0yjtz@X8Splmmc(ma7aGN!cA=7LubdW~Do~{Aod-;+UQkpx;bf>FCn*wPp z;DVrGDdC~oc`)r&Tf=B5E@GnJE`S8z^ILL(@O$Ovhmll%zgv&ISPhM(OvIJh2@BqE z?AsXx+$|lKyZ^!^9OALMdHnHT3CGivhS6v6vUBrNb-UJN^`h|1QTJiO{V(SlAQAVN zNj6mWWzl-0537(}^v%Zif^UiZguki*Yr;~~ZW2=5yE0sV+hg zE*UKePYKpD=DO$46B7>G(OGY@a6Oexzd1Tc&V<8Zp~>%3cnlkPjdIZnvq+BFe|TOaLQbX?!eeF7@$Au1n{omF-4#V2y_*?EbU}Bja zX$c>XVn1~@hw_7RN(=qC5fPBE;f!Ity4ZwV11<5EcmK!!aJ;-LjGjSrkJ?-^L7>K? z8e-aOG65iJ;~)jCM)-F$q>`sNA0}ZmW<@Z1m7(adH;V?MAMeDb3dCC-Irc-cI`t!r zOn$t4;}~1u%rJ_m?qaT6UU(i6Lma7%p5u{iR!D-8w#TpPx}Tt3#hyjo3BXCO9oJ$ku=Nz%R(`9 z8jnj34k2r*9hp#}GEaS@&0nI^8A5PLe9R>ofOV6OY=ZMv;H9_Nk9GDQqXAxM(CkkY z->;q;B&vA-h{tCv0i2^Xw?cY(YErokd&T==;{md*zr5>9?Q~c4vtKW$wc+wd0E~m_ z!FSQ$otD+GEa$EZR4V$W<|?8cpry@?7=Y-`Zq!<5{JACFu#mf;y!uw8cfY~$euEr; z@n3j_Oq>PqQe^y{o*Sx5aUJGsCu}m}pFr;*2t25L!mHb?Mp@lqR%3If9Xgl+b*O*> z3$)Y@t4Rnb;3>u*;bD&M<3cR@`irvecmvyCdYQ7vJy`Avj@ebzvzHvqekGRI^r4x( z4vrUMQBLQShj%R*Nf2swAGnE+(EnR8dc3+oX9KI@KeDI{A0!5S?HiYIPLiS`69CQ4 z2!qC(sxiRQ{@vmeP8PP5a}fKj*JYhr25Z$%IcWHM=f6GE_qqY&9~TmdK*Ha`vL)#S(2j!i60^8y&f#{B!W#DQ4ESO ziLSw`V!e7dWM`?Y@VV7Sa9=qz-_KZ=LpI^Quf81sm#j2^^*(x0{pSwlpe;%)jSMv? zYM)fmE7Ac~hiVJ{i|BhC)k05%`9WhBQCXX@SV&bRQm;*gnP3%ML{hTzU-= zRg(9XXKf0?{Jj|o`9`O1@Z>ke*4vT8HOWLxeuXeWhXCsf63Ce$40F=9%JcpJ6ak?bMiZ7cDY-WdD9oUBNU zN0{R>N{#-YGFk1QuGHlTnl5gia#vh2?@8%6_?47?hdJh$lqZEPVh+$;<21EWmt(J! zAw=%^(@5isYEmRW6EE6`LE3`dGW)5XN>D51e|1;UB~nK;1R2-sE=#z1@ea6HZGjmXa>E!36?g^ zE$Z{xJ>n=Dd78MuA`K$ZxO+XD>Ap{IF=eBnWKDLY+{Qlf7_$@R=7+GVwPcWkTVvw- z7nalDpWvvX=&UT3Wq3-^fDTv2Vr8$&1hN7!-3l5sMzUc{cY@USkQoIHC44Ak@hQh& z$#lr{s+Q=3fT{mqNc~fhy+cmn#gwGjy{tBr6a&s83R_4L;fz&p1gUGdr|1wyKJ6tf~CS@rJqIDen;e0NL!6ySE z#zf)%*@e;z4o)j69N)pIy(pVJRHq|U+=dH#%C&5QUIqz4$kNT3A-c&EH*Kb7S5K)h#I0Qc_DeTwp@_N>qkiV}sYQfXe5`)SC$og@w?FamxhsK*W za)3Rb*G?FGSe|-`7fLEBZp<$9PuHE2d#v{-JRY)Vo#-T!5C^B%SG@}EHi}Bm^Q0oz z0D6empdr}RdbzHX4PkSzSOoUKw2!H=9a48%#X&;b6*A9Gcca`OL5H^45XRmR8lN{b z-XzOF-?tXVbY;a`H3*Q20)j{ax5NepDI!QOky0=1=4LVlWX<-p`TLF;cFNywaB*w` zFNx5fHo0nsKw_irXX@R(Yq#~MV5OW$-=J4Kvbu)5$sB>t*UT~eX@=|J-$@6nlbk1_ z&lbHO+xt9TD2p)MEnz?5E+Q1RC^tSv-9RBZ-A#Ss#IL3B#ZC`Dogvc19E{=Qs9n7% zAENx6H7k0$!P&S8OdRE-OL>wF#6sgMJ+X4Et3=q(yYD^EE(;@m@d=*<-R`^Qc)4H5 zJPH<|R#~KM&>a3{GWfk6x0Z{AewgahR*U}Zm=hx)BgAH^%25LC(&WSpH~y4q{t5e; z=g|6fH2SL<1Tcjs(fq2h)w**(oyUN+aODtrhC#p)7$G-4tHlz8+$~h_`MUxOEY%7b(1iOpcFd>Bws%&sGt1?v zn|~5GXgGt1S_Cw33MK)A#9U~)1zl@SV~d2LCl5wjZns!}SG}Wj3T)iZpVh6*%--h- zAP^SjaMI{2!EOrmKI5MiG}WiMX*X(}V!NHzUeB+H=iSCYxCgC62W=8}J5Ci)ERE86 z%TNh9?P|16C{dMw`GTE1u|6NRn7lQWSC~X0L9rb`wV);vRX=b)xye%8v8x0#yRInA znA%OGEY9cLa{7BZzYo&IH$)7TqS`nUY_m{3w¨&9nukrDCdo9@Kf|bKB9d*&_KG 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 literal 23599 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 Ef}~nr{Qv*} literal 24136 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 KMNUMnLSTZ1zCoA( diff --git a/test/python_tests/images/style-image-filter/sharpen.png b/test/python_tests/images/style-image-filter/sharpen.png index ecae501ab77f0311d2e7b429b5b6fd01b7b8a2e2..592b9f650f9bab6392db4fb1a88e21e5bdb84b55 100644 GIT binary patch literal 22744 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%0ABo&GKMg5Gu8WZpzXxS#1Fltf9S?;x`1tH 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

literal 22760
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ℑT^12n0DO$dMRvv4^{(dNYWWQ1#S=gJz}#p%wPZdE*?76
zR}H6UJ=*WSFX4P26{P5l{6u?Y?o+g7Fup>uV7q!$K$(XThwKcoy>$wm=~OZ|dQU){
zsq2#zE!EQvOjc{cr2JbZx$riyLguK|Bkw49l2N~^D&m?&OLgNyXOXVgB8%kj^t6Sg
zT9*qEa9bO1F{cUHhYb1Nr~&MnzwQlLgcSPc%ZMx7ZIAtZ18Nj25TsmI$I6FmeC-XX
znmMPnWJW5VbOi9@%~*@muD~Q&pC|Kb&wd(l6xTyFRu8#18BTSp;{@k-wf!>Z`epC7bq`A;=zomKt*tmlMu61PxIWG7?4gI9llGwjHh$vl-fl
z(!Rmto^U{NuIs_=4++s%260YQr!e1re8RY#yiFT=wOyh8(JQr=f^5WwYdD>qzU4=n
z{^>(>BOO=uaQB7xmBBe;Ei2jKU~}dW%XI2TzF&ca=T8L`VPwfqOB_%I52o*pTi5j;W8aMS_AlBBYG(9uVIt3M1x3Og~5vkPn
z!2F7>21FS*O_wSe&D&W;a`%Vzf1gFY%iRw4;~<%_{D<2}$c0PtPh33|5E2!+{^Op>A9-WVjXzk2K#oMhm*7p5Ip=`_FDL&|D
z>S0~*Pa9MWg&xpG^_pfveaL86v!`-D1D}9cyX@{r4XVl2b4fKkT#N`WxRX%lva{ow
zbeIWM@Z_)LEX~-P1uOBjf?IuC4I>=*t4WC6W~6qlXphz!@Up(f1=pk|+8^xpR}l2E
zio2*zO==L#nCfYy-JcldrTHuUS2Gm52The-@*q0&$Ub-8KiZ#Elyg)tAO-;MbgMQR
z)zdo)%`_!ABkg{>JI86KSD8Wr%dta*O!DRWdpEmApE7GVP8Ek(_5rj5
z@+D2wZ*$Gu5F
z1~7wFCcuHQ73hBUZ&W8?i(k9>NO>@as|!UzWM5D6PG?qY({uun0O`Q?FFc=b!VFg;
zIn-XS*mjX7b5wf&&LlP>1GHd*`o$yfTK~(Y<8R9o=VS>Ln*)05|E;ZYAq5DgH>F?i
z`>~cR=s&gYP7%Xx2}E704t62C2>We5d214?L4|GT)xLCh064P@jPoy4pld(6s>K2%
zFJxZk4iS-r1FLqMPy!&4nzD2--tqetqqe8pIziq~np!YY+EvO^O%zSQ11X~d=O5^r
z?%gdLIyGs|*TyhdYqSCLTFioF$c}0<6@d8LnqR8mxK8ph$*qk!gqAlp(z#G&Tts1=
z3cwShRxs6eYSf(`L<~&455ANuh7aeoaRCXwIP)IOnv8%G*|Ld*)XYNG8s(m1kBs^j
zDE%C1<(}JBxPWIU_$29&#iHxOuF15vPWCo5o2cE)#w9S4H-X|$2g#ZL=O*x(zyfx&
zR=T!I@^~CXSAA?m$&YPX#ae;RWx#GXkWLl7DjP=ClChe>w7*md;x$nt&9Nx`%|sEpiPyubfb$iirAj53)>2~qSXLEyazvpqe=Nqz59Lv
z62Zh^GUH!Q9+7X&z7ClZV=7hY^o?E>gm;D5u)hxqCo8`Oism{me%o9rI6f~Xz6}qh
zISaN0*u9GA37DAmOz?mB0!j)zIR)Dt?6?lhPl2&F1C)f4?AtdLPCOzb5
zVoJN=7BNGAi}_V+f=pN3K_40aLaI7P5rW-}#3_E-q%|{Ng{(-oUx?9jxu8o}TQaB1
z1-*rsyMSKV?y9zF{_cE<75==z+#WNV)%G-sO4uf-4yRrzqW&T#;AM+on<@JIVV|yM
zkB3x;Z1K-Mn~x|0+Bw(-3%|=K=|BI!{4)ciq*6C3c6X@P-c*JV!wzOnZ$fp6#$i36
zOag20Va;l#V8wU4Md|rNgbdNWwe9uHzUgOf2TIeK2JTaY+Bv-itfS_?PzFZY^=iKc
zTAKfh!XM!2O#8PTTh0*sN(U9v-Aqp)JeXh>MC**}Rr9f4dIBuA4_Z($-=f()d_oZySU2CyVo??-)
z{Qc|>`urzNuHtYXK~4}i$xti6iC@Lt#OjQd7bt|lT-7K2R&*fzEG9M~qiq4>&y+4q
z9rgsN8+KT6E5DLrzU5%O-$7i~jm6KE{U-iF~<&O`LD<4HiD${gvP}+7!pV
zIb~V;%JHcGa0b`BJ|x*q@E(y2>4eQK&DHXM_ee-IaZnRVLq7_a?tHCJ_a5xR@O)=u
z)u11ecl8v*<`!_h>Kyenn#fo^Xkf_HU5XjMGi@qh(4>T~kFqH70@^s3rh6u1@2zoP
z!G{Qt?ZOr1xPOr<4)-I4gF_R~fX4kn`3rghGD=^i10AXhP~i@oYXT`w{S`C5y~-qN
zd0{|l7WV6F;ZC&-VmvA4Z0;COR06CB4!^S&Ec?71xfgMmRP
zJv`Ak*N;x;_X7WbcTm*?AnDWlY}49uvPzw1QG`q5v|2kP_pCOG7qAWJVcNCJ}5`P$>AGjjD*0jVWBp!TMc*B-aASPJ*21=ujK{?Uu8*8MXm
zb9X9;jTc5A_zxjv!u+R=I;zlpPNM5?r(pkw`kE_&Zy5i0QRIl!!u_*9>axR|Y@89u
zgQTIKg&uQo-;90HTL3;(5Ehv9_}gLS{AR8*e9U4wdSw1#nUFy~WL37QEGZo7u>LM1jas9{{2h0Q+Ok$7>0E
z{_m$LuP7I`;cf&Nl%Jp3A%sTrD%f0?i=MQ#@e^GS8}jJ&iL^wgnb0@hAN*=&-R3jb
zSC1*EzY@rAa9CcdMf=L|tob@qDjBP1(mt1R6*HZtX;|Nb2I0rW3;56m{E9;$K(Yy+
zGP0W=<<_`H)a`wJ^S^ocu}QDptBD5jh-}@h+pzU<(Y-kVzJuH7;_(ss?l_T{@P@@Q
z(LIdyR@gE#vb4JL>`_w^3pCA31N0Y`mk_I$W)i`(D6ND6h%7aPd*^gvn}JESQ{^~3
z_qHK#`EWRa=5>#3r}6EoHy`>;Gib)W+>v~|-HK}p{UYSRQ
zH4zC22#~ru+QePMckgH4lxrdBLOP^s-d^6OxiV;CYrmUnM^x<;VP8i33QaO&t!_!Q
zZBu}*FocXO;hw3)9A*4^zdXG?3odL{#(+0K%iGNtBQ!d#HS4o^x{@xjpYHQR%>rG^
z>|~eldf#JJ7YU2~Qf+FBPorH8$O(ahD3!fbBYJ3%G~^5DWQyyn+ha#oDiEH%nf&9q
z1{;{W
zJ4Ipc8dX?Phc5OP#mvl8zLCA|9Fk~*nQGmxKXk;3l@wIgnF;r7Ua|;JU=F+#9LB;5
z3iyezWa*!QB46fpg<2-<0s(P0i2rH{yK*wB0#U+rC}_q>`|%A96+74qJEDOnrUZpQ
zZB(;_!eIluGDYksnV>QxL~UsreHPRy{Jpu+mQlMYr0?JiroNaAqY+&XwP#yxs)W2U
zy@8<;KJhZ>3ZG<^$UsPFL|6^AS1g$9CX9
z-{5j)Khy4Pnf@%BK8F2q4B1;adKHpch6cQ|Uvv$-zil8~Ak?JqLO)mxv{N_ypN5%W
zBJEmS8DY}($T=?*p3j8S=?$iSSMU#^f;(#Oh099|
zB0Gq<_0R>Vh{a;?dmxNF!Q!xLaASpD*sl8|8V?!CxL01t8#R*fEA9(Q0)q)0^c4CN
zgzVU?Y&6p1bVSS!HaE=cwlB@>5x?!$Svn7kT+vmgS%s{5`-RQ@4qX;*=8E-NZXj~m
z8zDb!#wO4aFgv=OP^&PpNd|gnRa4;r=8!Bcp+!%FozLY9A%)0EoYL?0YR4s1ZD!NT
z4oNR!GJ&NH9aNmydPZK?{ESP!jYx7`llQcYn~M#QPEj`7moa|T7}13-&hWwS*JHhDlD>>^qq6b$aqA>&2ry-!XJ!=Ans5Le1p?S
zk@unO+FU18r2^yog~K$ejP#auvpvo*AZ3*
z@zm4r`9D5%Rz47VHMan8&4ZC>ivLi9^NJz{D7z0^sYz}rPm|?Gq>H?aVemQV_=^YW`~b3yDKI`DbC_r^#;@
zfp|gmoK_2g60}bEi(Jp_F)|A@BVn{jlcJ8;uJ78&v%Q_T)WVw7
zk(x-(5vDPp9Cr4Injb5>VX^9`vz$Xq(tPS0AaCZ$T6@8aV^iOxNjh?Zcc*92VNmTqziWVdsyDlWnOF43RkHFy!HWq)#)|k{l0e_A
zaWn3&tjcd2&K5Sk&`${oIn%154Y7EH&!m3M;ypnZS1u>vg+X|Z_Uk0kM2k2&bJdie
zk1@ro?FV<4RN|kWXc)GSe^QjL?fKSGjpMHK)x6@;~wzv$9U{cj3e|o7lAnT9hSV|4zl!=j_g_1KA{on9z
z8mxc`NFfY^PcKG8t}W+Yxf4b%yNM!~-|wuH5^zHfDP-4r+85T5Wu;;)l%X}#d;Jr5
zUYym(qfqE|ZTUR_q1NJ53M5HrWR6;!sgd5o%MY`P5j=spNQ7B9*erW4Wk*_mUh$e_
zMev5Frq?9IyDNzSlHLF(Oi&)O@<0ZS^5F}mG82UnAS`S<-|N-Exp$K!gibOX#qXQQ
zTjBj@)-sYgzL@Wn%4H(1Jmlsw&^6O13Kp`xh-H8?ekY@Ii3eWHlIx;h8L^|?tgEy(
zg~s)}Bx`>jCpG@CFb?j^3qU8|*hl?qT)A;G^$Z%T0ayI(#(j8;yY`<}V=Hs>0#Z}O
zCE0V6X=zg4lp|SGrNx{m`3FhGnV8O%GVpVk#jLzB*ZIkR;JZ=Sx|~On`NPy#ZVAo%Zsp9Jj1;-(Y
z-wjT^BdRn`T|c#}Gwf;0*dBYm#lN&(Fs@te*!^lSZcP%mVKlnH)>Q}uCc_o5JQDpK
ze+rgCI=VDO<6=zt8{i(wySFSA^7I)hZBuFo)o?ewEC?}JDo5((?dz4EFuJc-lT^jW
zQ0w`8mJCiFv9ZMi-DWq~l;UQcRxM|aG0L)kPFQp
zAjgkKkVFogXxl{#Uu61AMwYLW_&pm-dt|ASsI}+Xj9tB(XBahPv(U=`!6trrJ1~f?
zKOhLhFdYMXV=`MSmhlEdsegIbUv(4DXOUuXLY0AWqh#4hk?!y8`u-}NmRLoAtvmBX
z#{RG;f#)vfm+#LM`!>kL+Ml8gFleWTMI^$$exTJu%vKNp;y6jss4
zAx$WBh_AdKEe?@=Uhd+~^jGbxQk49J2-_B=%lwnY7Y;(BpN#9|7^tav?IYE_HC12*^Ku+M@2ZEshc*6YtS^jl}4XsL&TqrwuA$|#QrM>oEVqeHRqOxhun;D
zI=D2R@p_NXG62Bk53I?yfuBoPRI&l{j^!T>YT8>_&9#dJ#)U@9WK$4_k(qdc%gTM9OY?RfKJ0&LXlh>@L?Sx*>``=dTEaL
zNfcYV4S%gEW#@zm@J(5G--jW(lER<_AGRKF=8P4Pv93^fF`b(Z7}yY|p$KNy;Q~Xs
z8N7v8&8^v0L-V?cPxBLFGhLE~1aUL{t^7th?etZtaa|K6{1Pf)q4^x=
z6KondbDI~x?y^Mo@qQa+F-ZJ?Qz#5VZ><~*R)^{qgu|4Lnz(QvbEAT9U3WC$@b^-_6?J{hJOM#mkAr3RjV^SMQ|U
zlEP-=l-o8xz5UZbt3YLdY#ZZoTGHlY0!n}^bnV-6lb``$c7OT9G4iX)xbdSmkoYxc
z^C#V(J=?z!X99s+lg}ZL>};A!>&JbI(uS{JH6v{9l#ySTRLTR`mk%NOu*P@J8rDt*}9C|!At
zzcPuxSpbSCmIN`vR-1@+p`6OGaj2IHn^`d6RVjg&CW$wRHg_{feS*vTvIz;`Ys*qy
zrVclK0Gm_|p1wgydJze{nkmN@C8vR`XQ)e^+t!sn2A$)c&9xZoukupw1{^7;J|NJ5
zpg~ORmJtvvRAIFn001j>6$m<<03~QzeKc4WR%%d+{w(i7o+;3OiML7Jyc1IpVkgq8
zT*~0)04eyUHG-3&IQ8`?kA2V$I9m*S!5Qs!y_%{eenQb!`BtV5#&9N^fJbCT
zd`6nDaO@RVnaLFh_xP~9x#CtE-$
z+W>Fx%2?5=lU~nMF!^AfB+_Ap%@9t>Zc-N^Wo&#K^=iPP&zL$ZCDQM*A9-nQ{;?Po
zayRQdM!-yi<-b(v@<1@|ANf)!xF@G%WLAY!Wd@-)I9JA-+%_ImzS>tbS54DbV==Mn
z)|0v18Pr&~a2grFbr!m&^;gMQlj<^;rd0rBCG${;5o<}FI9C5u29k0JFeHIM8!pI(
zFB(m~L#H){GL#_51FSsQ01_>^AX7zwI)InmeO|jXfm@bHcT|n|ln4*$ktbtpMxxFU
z|7n4^32``wN1t6iY-RhBs6j=>vVe{{-jxYO8Yn8Pz7FbU4w^y*1XF=eNzX5Kcc_!~
zKK7Pop9Hn9PaJ#&Gjj4>NCdZ?UGEPcBIyGlvS`0Bm)ZI_;qB042)IBPQFj?h2LIt_
z_g7E{`11`4zQpt*4PrPhcm>Y`vWrmR{x|Rf4kS3)d#$}+#PPUEJd7h$U_AAg7o;JD
zidt}C*uY%3I~I`iwRh?paV9y%Wl=Ykj}0YOb9#96s&2v1F{3<7U5}L8Xlz2GKa|b;#h{@u%9We%=qBhy+xBcI5Y@ft^0sEHdB!
zhFqP8?hAA|v
z*qMTBs@;2()@AR3hsqqWcEh=J>6Vehz%j@2a5OTctAe&(*WWF^EKRMqT`{
z89h)@Epu(4G!adS`f6N_~*Owx5WmqQ
zh2UOMZk{7!$yxV`*A(`KEU~E7jEV}vWINDFvI8?7wCG5uT572+6;&?+@9;nLRLT%U
z8;zR-72d7pV{BIU&&*2^%A1vMjq5L&&RHEM{#yYHk+T03V+QIB*oMffI}T|b!G4Lb3=*KsvA2v!1p
z6(?_2_#7XW3+?@|!5=aMrNMr?hYiHr*RmKWY3q1S8)cgy^Y5mRa34bnTnYZnmZ=Np
zrGRP*0jG)YFMe{pic5BHlE6V0Bo3SYf;!u-hUdO(!Xz+s#JnlNu)k(wEteA8Nfjp>|7G0Y-m%yGTwi>CPMYisOD)+8-|B
z^n>S2m+xoHAbCeW-co_eR&N!fY_~Tl(Qz}D2ggq(4P}lEzn43tn$Mdbfj2N!k1_C2
zotY2Vmm)qEx8%YE%tsoU2jj-QRp=*p{mr4+gLL^Ty{
z?L1A$3}O34FQXh-NKy}LQJ!7*)I(Dww$0k%b0Ye<43&KQ
zVvBZ=`16;+?J%V}>uah!Jc@ik?O)GSFIk3=;iM$2Qp8SO)>4(Abh
zm3dxTtZJd&5={-$a&IS_)ixHJzJN1WcTQuU@U&Kwq-mhE)_{?dolLc3mc@#IUo2Vh
z32*j2?$UmPwt($WauX&>|7#T|g4)y5@rV6@GSOa&ag5>WWlTk!J
z20?pahj^V|{7!8B`!^~gs?OyTx6Es0j_NZqlYv5kQ90
zEvEo(!fCJFZ=633=j}jh-k}WsbsK{$7mH$b`wuMv`M2XLHuGB7;^8l3r(w>L{omeG
zn8Y3`4+80nH_)Pf00?1{tV4BJrcLo3&wbtS+-XC$*N@
zKezrZs5H0`#{Lc@O%@vtKvHxI=&KW(3`KxCi%i45LW!^C+W!Lf776Lk?DN!0t`q0)
zuw^2d^7e@yp$fze7OGh4lJap4^xtwi6*&wjw4u
z5DAYG(AuVzjNs2R?n5d7XZEjS%Lx%j*|uX_mLv5_gjPbVJ|r>am+Z(PE!F)g$qRry
zd2=J7e5p+q0h#XaW{YsyR7%CKV31&sngPQv>cuUN~1w!H47NvbGZ07?L;
z(@tdaVCq1V+
zqN=+_X%nKn07zQ}q;-5v=Tcth0#E`Fa5fb&_nx!xUFx*6?5sDMZ)hbtfj<|Pt~F6-
zWd51~YxXS7d;t~PNWN?JEv>NKa!Mt5-0g<*m?gZ{$8%x;vN5oBDXoMUrliRcs41Pw=l;@kEatY>?bO^T
z^;J-!x<3UFMsa)E72qHYQq?hDl$JnpP3CXb7D_)m};O%{t=bX
zr?(AucuvA*_i<=GsaCF*LW7y*(dlqaEOj4+oGL&jK7RbbLSdyQGsVY~Q;zxuNRxaZ
z5S6UK7w+KMs~l(AyZ7n?dnlUl!i_XmipwWzx6jIsBalz>=b>mrsX5NhA#A&O|GCB>
zBKd2e^N~PMY5wrZYn6T9%AK3eNl}9G*K;p}#{m=@1PTu_T6jP-siO
z4A6Rlo_ec65RT@p%n?a&Yp}ADbhQ!_z@>A>_MC+8lG(YNyMf*o)?@z}opOZcRXvuZ?W?vUw
z-x=XOpbkrPZVL6K;2zp`B>Nhb!+Gg<+CS{lec6AYXg|u=FFRifd8WLAqEqwzj&cF`
z0`L=FNE(LgmQXN7Kfed3GcIh(E#KQ`G5FAE(TVz{K;l-RXHHjO>e=_ln0D~>a>B&1
zUD2$aG3({$kloQ|%U|{wH?%9}jPHxZ(}uv+VKmk)nuyMW8nW)d^#@f&{ejicpifO$
zx30&8!%xV|Z;b=aMI03UIdgm-O1uCZ70gK*YcEDH?`TTx<3edb{qt$?%`0zTU{1(V
zl?gVBTMU0;gT?@)VZh9WR)S?GJv6m3#d?9%MEKp#Gx7KGX|i^HP4HXegk>{_v+lry
z`n1K!fgLerq#d@eoGxs4gzuWgI1&{n`t#@bJd{WQ2#k?<@uh9{r_!&pvG%5)T)^7y
zk35Kj%lR#+zq+C5WGrgvEvN?r`$lNm#u8S|jM1~34P54q%9Zf>fv=|n0yp}I{vL3A
zK1!SbM5R7q&39*C+-F|=q8wwdxI$-z9wWVJzm9BX-nJt~W89)um^j%1ex7p+nf!Ax
zf5}?W-vf@qL5UFnnoWlsc{IxI;>gusRr6iJiLZmYvl_y*Zzovv>WwjrT(QOfY|cH4
zNJ7ATXZU+M3MRed=aFAH-q&p|oECaA2b|dN14rSYLH1yU-=E-lfwWH`n6btnxG)2q7!!XNj3tV;{VMB7e?>T`TNAu>0
zJ05)=_EYA=$8|1z$r{MTA|Q*wkBILv1JkE1#L=iLqQ46qg^yw_094;6C*R@Qk!*Nv
zu}LTv>drM|^Y6`Awehp>Y2e-voQ>EEU+)F*_n6B(`u=OONiS3t$ie65IUD}&^AH_*
z2>u7cM1K!Bz8s3B08l5LOHbc0@>6|Z&sk4&5*9V+KO4@qfLX6D%(2&V%B(`2f6p&G
z5l15~;8fTdghd1(D*O=6LGaz_OmrfO
z3EgG-7%fZeD5oaFXqW5<0BYm^`+A^C*zUIqy+!p{-GB8z
z!JBYhe^G>Ii5-ux
zuwmN2BbII99d0jTcedW7G$cUO7wzr{9xbujDM1si>%M1Mgz
zzHStm0EAq9grxT$**N?E+zLUXwT(q5S#bsR?jr}_-rxk$Ul5M38(&-i$lRy){kV)*
z*q(R<4OUx-PO#z*eJ5kqyHD(wgX8PR7Zrf;n;E$I;S<8s?qFTm5e)SiCpx)G0_u%z
zhE8KAiT-kMeEs+$0zlJflar77?z>+28>a4Nu-(`Z`;t$KPOjn(ot3&U?bQi$JhqDd
za&Ub8D0Bfh7JFA9zGNEhPCM)rUhZ*0Gesv@afQQaXN>h&4Ab77(V#~U>^c@N`pd!b
z^`lS)z&AXZjm8^rI~Mvb`l6Gnq@k{}A*SqHiJiwe`8kRPg(d(euRK7~yAO!ClaAww
zDQN87Ty#Q}G?4kR*%u=Ei^1`2;IjmPWd_zn(!Uhs_GCpwWzB1kl8pik=e@45G+=r07vw}sCV02;lg|K3sT
zMIP_rg05bJpzl&wbW)Wh)ScN7_3iA~K%Zj23>@Dc3M>GjH_};5|34Scq1mF&Fdo?o
zJ~0Wn_&S4)?
z=UQ9gIHTdMFnI1F(O(3PZxaO;fWWh{1t%3XgK+F$w6`hPl2{Pd=
zCRIVr;bmYrHfL5|nw(P#_M7l+@JAV#jV_A;Zk3_$tPh>#x-jd}6-&1q7X3xw_%@Mm
z0ic09$m36ldHDb~8*Ld8Y&O_3&;RDDzA$h#6rGqw0SnLCsMxz43`dtyJDs*VFi{v&
z7L8_=Maw_y!?I^D>4m7XuGvD1|J%YX6svuPRgQ!uCp%6_bdm~
zu>~VO!E|(a*miA*-D~IIZsIxIOT2Il*gjKs2pDgxe5UF?4x@Bm6vZ3BfOwAs?Wvr7r6ZPIrH{gt!*MYDT}o9
zUr_C{N`69PJAF9LA1cr*T>z0T3(6_^!E^XU6io>nAXs*vK7CTT2KjVU1X1Gn^3W;(
zWCC7${SHSTUdG&zW$3)42ZryOiJ1G(Fkt^k(aBiUAiqb&p5<~p`vo!m2UbJ7->iVg
zXBhd%nv}w5qf#&{RSF|koQWw(uMO#)3D_y
zWy_;h1|#EnCR?UsZwLiJ>O;wSuHSx&kl4GTzrY+{Pyh(~L$9N`R~v-@pV5m}V$ilJ
zFj{T~1Lu0*j6=|LPIVZJDR}8`HoiO>w={->{ebL}Um^hXeI?8vzWcT@0?Lz6K7GhG
z(esjss238`)NXr~`3~o=ry=Xz2bFE|=YIA|)iO~|Bno1`#2jBx00M*(Bbuu$(2sAyF*wk@8VvIw0JR5}Mx{2TQK60GyH>B#lDhx6
zau_|s79sn+pez9L)c|D?P!@z)>m%^uwPb&?2&Cpa?KjRfM1`a;-@H@FQ{Lp4-zLA$
z(w*mI%LmWglo6ixS-R`IY+H1~L(yMkjzSgyzsO`3=|}DT6y101;U#Ri=z~eymSE`m
z85rp|3AUTtGpCr?#4IXIaIeDJ@N*-7l@`As=1vTfGLjH?KMplo{VWp!v+?CH+qtV+
z0eJlAhFa1q3jnPLU%11T=WdKtA+Y@ZtM31jrJo(n_cT
z^sfTTF1l#j(*i!bmnaFqYlLlb&bI)}7ODfe34l7}CJySB$=Xo2@4NROM1PSv3RwUM
zJ3`J&h`&M?`U{M)^7u9c-H#QWh+<*3XQf=L096D5IGH4rtZ6B@ntTDt5AGo5vLK{&
z>!L$@D-0jd0lPeB3$%FvO+J8sPTj~=08$>jV9T?-a~A+jDZc_Ra%Hdv0r)8Ti_Gx_
z1c0zL=qz*kP51P~$(u>&wsim_LyJvq*vLO7?xvy>v#2n}qpBbP+N%IYgDRrBkq$!6
zp2dySyGTsEhvD7&W6$Do@b{X}5P5hrG&upO{a+iQrRyI)ek>FLP-iV@%7>}}TmZf<
zJ*~?|#nJv^VpOt^jLWBXsFxjk*0sVE(X4_)Eay
z<&$LOS0@0{SO9mI(P};QPMf1uOn3?sQb$@%f}ySopuCMr_}rX;TmZf<}CdQ
z75FR4>zir&mj`tK($`=CP!nIHj&;$djRkhO%v2z}GD3EH$^;+>nF{2hHhK!SkxwZP
zUm!n8IlAv&#w)e^<)yt}TjEZ@l8bx^!14Hda67-fzy#7+p~HL$bywCCoy-Nr6xS*$
zEdi$E%EL+^zfDVXtaciwmHbj9Uy2k6N`W{M^FK9NV$xIlJ~{X(f{*SwHP2BAt1i8j
z3*>n&koa2a6MXzAAw5+Q;%{ZBCH?En_qcrPF>a^5RGTlw|4aJ?kcd#<0BNF@0*W@2
zipx7;zbGCDP-2nq&Ook5d||XI|Mh-yBpQ#jMFTrKbogT&EJt-g%jI24+-$(g(SY@b
zR)%#OLq>j2r?Gh=zZ6017vcEU6*#(S8N#B1Sa)l6_nbnqDeU%i+&vb)8x)-a|42zc
z0a_0fAipn(hp${-0g)-}Sb}m)f1r?8sPH?*75GO;j-~6MJ|DC!?T=wSLX+UO`#5I&<5HqTfT})K233I3m~ybNtAi#sCg@|=5?hzq
z=ZpMO_^olkRfzhm+k!Bq1vXcIo`(;=
zhhdoC95~;5?mg$+!{3?hvkhI<(A~9&K+)fc022#cQ6dJr>n(fk&2tkFu|3%|0>EI~
zii&14G_513>zT3oEK#F|-=h;YcYYR)D8jt?7T&MzA`ivM*oNgR9p~#
z!J-6<(>E5y;Z*V43Yoj+3sWvCC2MvAqaYrbETaTZ;M
zR+tQ04EI-J*y8N$Ib^6sx3QhVePYwGr38SboXSR;Z4>fm*+G`-43|@$a1RJX>C;}}
z|DPZ>nk^*&jJn>}@GkP_DMyD`56D#teo*Le%^l7c4!|Yc3(6p0%YNMxj?sHypQ2p1
zYLPp8niK5fck;9*OIf=5`|)!KuZWAtt9l{)e-p(2K)3*~i$^*}7oZ=1%cl&tnCI91
z4m%$RO-SY`$MY%KI39HsdqYklA}IsOB~>WYcA)&(5OOrlh|ahJ->55a4Lt&vvxj)?
z0(-K7oNOX53-5nA`{6T@2)mxj)0zdVE#QHC$>5yR~EXVpuJYO
zaR@@{2p0hT#3GV(#roRFZug-}ftwB6&v4Mq@BLWlscfun5Y
z&obTrr)$Oolj871KPlX31R)iK2!LUB32lp`>zCu+-T~Q72gs8ZaEbgrlI&iCQMl0v
zLMqr)0N6f$Wa$%M{d3Lbe{gy`Ue>D&^ySrgto?R>*l8TQ6pd7Mjc|hzgp{zU0I+Vp
z@s(wS*Ii!KYAb_N)IKOee0bxHGT4XT8+a}`leY$oHV{Eb8JlkbGMcL4oU4Fq`ffPH
wT2}g?qwoj_L_&TUFV$s@H);y=3Bo3P14DOb76EXk4FCWD07*qoM6N<$g75E5E&u=k

diff --git a/test/python_tests/images/style-image-filter/sobel.png b/test/python_tests/images/style-image-filter/sobel.png
index ba2e564fc3c564d423a338cfc2c490f648d5eb7c..f7061b378d88c67e6f0065372fc2c98c7d3bbd81 100644
GIT binary patch
literal 23931
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
b(J%ZTB?#bP23!DZ00000NkvXXu0mjfBI1Gg

literal 23955
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 E0QQb(GXMYp literal 17232 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 literal 11508 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 diff --git a/test/python_tests/images/support/marker-text-line-scale-factor-1.png b/test/python_tests/images/support/marker-text-line-scale-factor-1.png index bc485f7a4ada9e690aa1db4160923271e4386bc1..23aee6b353d29bdad81e6bd55ae340e9e6a69b27 100644 GIT binary patch delta 17557 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

JG!tLYJ1vn7Yi$wY|4i19!37?Sohgk{ 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 literal 8369 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 literal 11838 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 diff --git a/test/python_tests/images/support/marker-text-line-scale-factor-5.png b/test/python_tests/images/support/marker-text-line-scale-factor-5.png index 7a9d49e48f0cb60f21c05a0cf488d428fb58dbaa..7122e287b82b8afb099cb55edae9a4fa5e12fb83 100644 GIT binary patch literal 13953 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 Date: Tue, 7 Feb 2023 14:42:24 +0000 Subject: [PATCH 11/37] Fix deprecated `PyUnicode_FromUnicode` (NOTE: shouldn't assume wchar is 4 bytes!) + Unit tests (shapefile, render_grid) --- src/python_grid_utils.cpp | 4 +- test/python_tests/render_grid_test.py | 171 ++++++++++------------- test/python_tests/shapefile_test.py | 186 +++++++++++--------------- 3 files changed, 152 insertions(+), 209 deletions(-) diff --git a/src/python_grid_utils.cpp b/src/python_grid_utils.cpp index c2585732d..3c5ab8b1d 100644 --- a/src/python_grid_utils.cpp +++ b/src/python_grid_utils.cpp @@ -105,7 +105,7 @@ void grid2utf(T const& grid_type, } l.append(boost::python::object( boost::python::handle<>( - PyUnicode_FromUnicode(line.get(), array_size)))); + PyUnicode_FromKindAndData(PyUnicode_4BYTE_KIND, line.get(), array_size)))); } } @@ -168,7 +168,7 @@ void grid2utf(T const& grid_type, } l.append(boost::python::object( boost::python::handle<>( - PyUnicode_FromUnicode(line.get(), array_size)))); + PyUnicode_FromKindAndData(PyUnicode_4BYTE_KIND, line.get(), array_size)))); } } diff --git a/test/python_tests/render_grid_test.py b/test/python_tests/render_grid_test.py index 8752fccb0..c5f0cf8da 100644 --- a/test/python_tests/render_grid_test.py +++ b/test/python_tests/render_grid_test.py @@ -1,24 +1,6 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - -from nose.tools import eq_, raises - import mapnik - -from .utilities import execution_path, run_all - -try: - import json -except ImportError: - import simplejson as json - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) +import json +import pytest if mapnik.has_grid_renderer(): def show_grids(name, g1, g2): @@ -384,27 +366,26 @@ def test_render_grid(): grid = mapnik.Grid(m.width, m.height, key='Name') mapnik.render_layer(m, grid, layer=0, fields=['Name']) utf1 = grid.encode('utf', resolution=4) - eq_(utf1, grid_correct_new3, show_grids( - 'new-markers', utf1, grid_correct_new3)) + assert utf1 == grid_correct_new3, show_grids('new-markers', utf1, grid_correct_new3) # check a full view is the same as a full image grid_view = grid.view(0, 0, width, height) # for kicks check at full res too utf3 = grid.encode('utf', resolution=1) utf4 = grid_view.encode('utf', resolution=1) - eq_(utf3['grid'], utf4['grid']) - eq_(utf3['keys'], utf4['keys']) - eq_(utf3['data'], utf4['data']) + assert utf3['grid'] == utf4['grid'] + assert utf3['keys'] == utf4['keys'] + assert utf3['data'] == utf4['data'] - eq_(resolve(utf4, 0, 0), None) + assert resolve(utf4, 0, 0) == None # resolve some center points in the # resampled view utf5 = grid_view.encode('utf', resolution=4) - eq_(resolve(utf5, 25, 10), {"Name": "North West"}) - eq_(resolve(utf5, 25, 46), {"Name": "North East"}) - eq_(resolve(utf5, 38, 10), {"Name": "South West"}) - eq_(resolve(utf5, 38, 46), {"Name": "South East"}) + assert resolve(utf5, 25, 10) == {"Name": "North West"} + assert resolve(utf5, 25, 46) == {"Name": "North East"} + assert resolve(utf5, 38, 10) == {"Name": "South West"} + assert resolve(utf5, 38, 46) == {"Name": "South East"} grid_feat_id = { 'keys': [ @@ -670,25 +651,25 @@ def test_render_grid3(): grid = mapnik.Grid(m.width, m.height, key='__id__') mapnik.render_layer(m, grid, layer=0, fields=['__id__', 'Name']) utf1 = grid.encode('utf', resolution=4) - eq_(utf1, grid_feat_id3, show_grids('id-markers', utf1, grid_feat_id3)) + assert utf1 == grid_feat_id3, show_grids('id-markers', utf1 == grid_feat_id3) # check a full view is the same as a full image grid_view = grid.view(0, 0, width, height) # for kicks check at full res too utf3 = grid.encode('utf', resolution=1) utf4 = grid_view.encode('utf', resolution=1) - eq_(utf3['grid'], utf4['grid']) - eq_(utf3['keys'], utf4['keys']) - eq_(utf3['data'], utf4['data']) + assert utf3['grid'] == utf4['grid'] + assert utf3['keys'] == utf4['keys'] + assert utf3['data'] == utf4['data'] - eq_(resolve(utf4, 0, 0), None) + assert resolve(utf4, 0, 0) == None # resolve some center points in the # resampled view utf5 = grid_view.encode('utf', resolution=4) - eq_(resolve(utf5, 25, 10), {"Name": "North West", "__id__": 3}) - eq_(resolve(utf5, 25, 46), {"Name": "North East", "__id__": 4}) - eq_(resolve(utf5, 38, 10), {"Name": "South West", "__id__": 2}) - eq_(resolve(utf5, 38, 46), {"Name": "South East", "__id__": 1}) + assert resolve(utf5, 25, 10) == {"Name": "North West", "__id__": 3} + assert resolve(utf5, 25, 46) == {"Name": "North East", "__id__": 4} + assert resolve(utf5, 38, 10) == {"Name": "South West", "__id__": 2} + assert resolve(utf5, 38, 46) == {"Name": "South East", "__id__": 1} def gen_grid_for_id(pixel_key): ds = mapnik.MemoryDatasource() @@ -718,39 +699,39 @@ def gen_grid_for_id(pixel_key): def test_negative_id(): grid = gen_grid_for_id(-1) - eq_(grid.get_pixel(128, 128), -1) + assert grid.get_pixel(128, 128) == -1 utf1 = grid.encode('utf', resolution=4) - eq_(utf1['keys'], ['-1']) + assert utf1['keys'] == ['-1'] def test_32bit_int_id(): int32 = 2147483647 grid = gen_grid_for_id(int32) - eq_(grid.get_pixel(128, 128), int32) + assert grid.get_pixel(128, 128) == int32 utf1 = grid.encode('utf', resolution=4) - eq_(utf1['keys'], [str(int32)]) + assert utf1['keys'] == [str(int32)] max_neg = -(int32) grid = gen_grid_for_id(max_neg) - eq_(grid.get_pixel(128, 128), max_neg) + assert grid.get_pixel(128, 128) == max_neg utf1 = grid.encode('utf', resolution=4) - eq_(utf1['keys'], [str(max_neg)]) + assert utf1['keys'] == [str(max_neg)] def test_64bit_int_id(): int64 = 0x7FFFFFFFFFFFFFFF grid = gen_grid_for_id(int64) - eq_(grid.get_pixel(128, 128), int64) + assert grid.get_pixel(128, 128) == int64 utf1 = grid.encode('utf', resolution=4) - eq_(utf1['keys'], [str(int64)]) + assert utf1['keys'] == [str(int64)] max_neg = -(int64) grid = gen_grid_for_id(max_neg) - eq_(grid.get_pixel(128, 128), max_neg) + assert grid.get_pixel(128, 128) == max_neg utf1 = grid.encode('utf', resolution=4) - eq_(utf1['keys'], [str(max_neg)]) + assert utf1['keys'] == [str(max_neg)] def test_id_zero(): grid = gen_grid_for_id(0) - eq_(grid.get_pixel(128, 128), 0) + assert grid.get_pixel(128, 128) == 0 utf1 = grid.encode('utf', resolution=4) - eq_(utf1['keys'], ['0']) + assert utf1['keys'] == ['0'] line_expected = { "keys": [ @@ -852,7 +833,7 @@ def test_line_rendering(): grid = mapnik.Grid(m.width, m.height, key='__id__') mapnik.render_layer(m, grid, layer=0, fields=['Name']) utf1 = grid.encode() - eq_(utf1, line_expected, show_grids('line', utf1, line_expected)) + assert utf1 == line_expected, show_grids('line', utf1, line_expected) point_expected = { "data": { @@ -939,7 +920,7 @@ def test_line_rendering(): def test_point_symbolizer_grid(): width, height = 256, 256 sym = mapnik.PointSymbolizer() - sym.file = '../data/images/dummy.png' + sym.file = './test/data/images/dummy.png' m = create_grid_map(width, height, sym) ul_lonlat = mapnik.Coord(142.30, -38.20) lr_lonlat = mapnik.Coord(143.40, -38.80) @@ -947,53 +928,49 @@ def test_point_symbolizer_grid(): grid = mapnik.Grid(m.width, m.height) mapnik.render_layer(m, grid, layer=0, fields=['Name']) utf1 = grid.encode() - eq_(utf1, point_expected, show_grids('point-sym', utf1, point_expected)) + assert utf1 == point_expected, show_grids('point-sym', utf1, point_expected) test_point_symbolizer_grid.requires_data = True # should throw because this is a mis-usage # https://github.com/mapnik/mapnik/issues/1325 - @raises(RuntimeError) def test_render_to_grid_multiple_times(): - # create map with two layers - m = mapnik.Map(256, 256) - s = mapnik.Style() - r = mapnik.Rule() - sym = mapnik.MarkersSymbolizer() - sym.allow_overlap = True - r.symbols.append(sym) - s.rules.append(r) - m.append_style('points', s) - - # NOTE: we use a csv datasource here - # because the memorydatasource fails silently for - # queries requesting fields that do not exist in the datasource - ds1 = mapnik.Datasource(**{"type": "csv", "inline": ''' - wkt,Name - "POINT (143.10 -38.60)",South East'''}) - lyr1 = mapnik.Layer('One') - lyr1.datasource = ds1 - lyr1.styles.append('points') - m.layers.append(lyr1) - - ds2 = mapnik.Datasource(**{"type": "csv", "inline": ''' - wkt,Value - "POINT (142.48 -38.60)",South West'''}) - lyr2 = mapnik.Layer('Two') - lyr2.datasource = ds2 - lyr2.styles.append('points') - m.layers.append(lyr2) - - ul_lonlat = mapnik.Coord(142.30, -38.20) - lr_lonlat = mapnik.Coord(143.40, -38.80) - m.zoom_to_box(mapnik.Box2d(ul_lonlat, lr_lonlat)) - grid = mapnik.Grid(m.width, m.height) - mapnik.render_layer(m, grid, layer=0, fields=['Name']) - # should throw right here since Name will be a property now on the `grid` object - # and it is not found on the second layer - mapnik.render_layer(m, grid, layer=1, fields=['Value']) - grid.encode() - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + with pytest.raises(RuntimeError): + # create map with two layers + m = mapnik.Map(256, 256) + s = mapnik.Style() + r = mapnik.Rule() + sym = mapnik.MarkersSymbolizer() + sym.allow_overlap = True + r.symbols.append(sym) + s.rules.append(r) + m.append_style('points', s) + + # NOTE: we use a csv datasource here + # because the memorydatasource fails silently for + # queries requesting fields that do not exist in the datasource + ds1 = mapnik.Datasource(**{"type": "csv", "inline": ''' + wkt,Name + "POINT (143.10 -38.60)",South East'''}) + lyr1 = mapnik.Layer('One') + lyr1.datasource = ds1 + lyr1.styles.append('points') + m.layers.append(lyr1) + + ds2 = mapnik.Datasource(**{"type": "csv", "inline": ''' + wkt,Value + "POINT (142.48 -38.60)",South West'''}) + lyr2 = mapnik.Layer('Two') + lyr2.datasource = ds2 + lyr2.styles.append('points') + m.layers.append(lyr2) + + ul_lonlat = mapnik.Coord(142.30, -38.20) + lr_lonlat = mapnik.Coord(143.40, -38.80) + m.zoom_to_box(mapnik.Box2d(ul_lonlat, lr_lonlat)) + grid = mapnik.Grid(m.width, m.height) + mapnik.render_layer(m, grid, layer=0, fields=['Name']) + # should throw right here since Name will be a property now on the `grid` object + # and it is not found on the second layer + mapnik.render_layer(m, grid, layer=1, fields=['Value']) + grid.encode() diff --git a/test/python_tests/shapefile_test.py b/test/python_tests/shapefile_test.py index 2558506d5..b0fdc91f4 100644 --- a/test/python_tests/shapefile_test.py +++ b/test/python_tests/shapefile_test.py @@ -1,149 +1,115 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - -from nose.tools import assert_almost_equal, eq_, raises - import mapnik - -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) +import pytest if 'shape' in mapnik.DatasourceCache.plugin_names(): # Shapefile initialization def test_shapefile_init(): - s = mapnik.Shapefile(file='../data/shp/boundaries') + s = mapnik.Shapefile(file='./test/data/shp/boundaries') e = s.envelope() - assert_almost_equal(e.minx, -11121.6896651, places=7) - assert_almost_equal(e.miny, -724724.216526, places=6) - assert_almost_equal(e.maxx, 2463000.67866, places=5) - assert_almost_equal(e.maxy, 1649661.267, places=3) + assert e.minx == pytest.approx(-11121.6896651, abs=1e-07) + assert e.miny == pytest.approx( -724724.216526, abs=1e-6) + assert e.maxx == pytest.approx( 2463000.67866, abs=1e-5) + assert e.maxy == pytest.approx( 1649661.267, abs=1e-3) # Shapefile properties def test_shapefile_properties(): - s = mapnik.Shapefile(file='../data/shp/boundaries', encoding='latin1') + s = mapnik.Shapefile(file='./test/data/shp/boundaries', encoding='latin1') f = list(s.features_at_point(s.envelope().center()))[0] - eq_(f['CGNS_FID'], u'6f733341ba2011d892e2080020a0f4c9') - eq_(f['COUNTRY'], u'CAN') - eq_(f['F_CODE'], u'FA001') - eq_(f['NAME_EN'], u'Quebec') + assert f['CGNS_FID'] == u'6f733341ba2011d892e2080020a0f4c9' + assert f['COUNTRY'] == u'CAN' + assert f['F_CODE'] == u'FA001' + assert f['NAME_EN'] == u'Quebec' # this seems to break if icu data linking is not working - eq_(f['NOM_FR'], u'Qu\xe9bec') - eq_(f['NOM_FR'], u'Québec') - eq_(f['Shape_Area'], 1512185733150.0) - eq_(f['Shape_Leng'], 19218883.724300001) + assert f['NOM_FR'] == u'Qu\xe9bec' + assert f['NOM_FR'] == u'Québec' + assert f['Shape_Area'] == 1512185733150.0 + assert f['Shape_Leng'] == 19218883.724300001 + - @raises(RuntimeError) def test_that_nonexistant_query_field_throws(**kwargs): - ds = mapnik.Shapefile(file='../data/shp/world_merc') - eq_(len(ds.fields()), 11) - eq_(ds.fields(), ['FIPS', 'ISO2', 'ISO3', 'UN', 'NAME', - 'AREA', 'POP2005', 'REGION', 'SUBREGION', 'LON', 'LAT']) - eq_(ds.field_types(), - ['str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float']) + ds = mapnik.Shapefile(file='./test/data/shp/world_merc') + assert len(ds.fields()) == 11 + assert ds.fields() == ['FIPS', 'ISO2', 'ISO3', 'UN', 'NAME', + 'AREA', 'POP2005', 'REGION', 'SUBREGION', 'LON', 'LAT'] + assert ds.field_types() == ['str','str','str','int','str','int','int','int','int','float','float'] query = mapnik.Query(ds.envelope()) - for fld in ds.fields(): - query.add_property_name(fld) - # also add an invalid one, triggering throw - query.add_property_name('bogus') - ds.features(query) + with pytest.raises(RuntimeError): + for fld in ds.fields(): + query.add_property_name(fld) + # also add an invalid one, triggering throw + query.add_property_name('bogus') + ds.features(query) def test_dbf_logical_field_is_boolean(): - ds = mapnik.Shapefile(file='../data/shp/long_lat') - eq_(len(ds.fields()), 7) - eq_(ds.fields(), ['LONG', 'LAT', 'LOGICAL_TR', - 'LOGICAL_FA', 'CHARACTER', 'NUMERIC', 'DATE']) - eq_(ds.field_types(), ['str', 'str', - 'bool', 'bool', 'str', 'float', 'str']) + ds = mapnik.Shapefile(file='./test/data/shp/long_lat') + assert len(ds.fields()) == 7 + assert ds.fields() == ['LONG', 'LAT', 'LOGICAL_TR', 'LOGICAL_FA', 'CHARACTER', 'NUMERIC', 'DATE'] + assert ds.field_types() == ['str', 'str', 'bool', 'bool', 'str', 'float', 'str'] query = mapnik.Query(ds.envelope()) for fld in ds.fields(): query.add_property_name(fld) feat = list(ds.all_features())[0] - eq_(feat.id(), 1) - eq_(feat['LONG'], '0') - eq_(feat['LAT'], '0') - eq_(feat['LOGICAL_TR'], True) - eq_(feat['LOGICAL_FA'], False) - eq_(feat['CHARACTER'], '254') - eq_(feat['NUMERIC'], 32) - eq_(feat['DATE'], '20121202') + assert feat.id() == 1 + assert feat['LONG'] == '0' + assert feat['LAT'] == '0' + assert feat['LOGICAL_TR'] == True + assert feat['LOGICAL_FA'] == False + assert feat['CHARACTER'] == '254' + assert feat['NUMERIC'] == 32 + assert feat['DATE'] == '20121202' # created by hand in qgis 1.8.0 def test_shapefile_point2d_from_qgis(): - ds = mapnik.Shapefile(file='../data/shp/points/qgis.shp') - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['id', 'name']) - eq_(ds.field_types(), ['int', 'str']) - eq_(len(list(ds.all_features())), 3) + ds = mapnik.Shapefile(file='./test/data/shp/points/qgis.shp') + assert len(ds.fields()) == 2 + assert ds.fields(), ['id' == 'name'] + assert ds.field_types(), ['int' == 'str'] + assert len(list(ds.all_features())) == 3 # ogr2ogr tests/data/shp/3dpoint/ogr_zfield.shp # tests/data/shp/3dpoint/qgis.shp -zfield id def test_shapefile_point_z_from_qgis(): - ds = mapnik.Shapefile(file='../data/shp/points/ogr_zfield.shp') - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['id', 'name']) - eq_(ds.field_types(), ['int', 'str']) - eq_(len(list(ds.all_features())), 3) + ds = mapnik.Shapefile(file='./test/data/shp/points/ogr_zfield.shp') + assert len(ds.fields()) == 2 + assert ds.fields(), ['id' == 'name'] + assert ds.field_types(), ['int' == 'str'] + assert len(list(ds.all_features())) == 3 def test_shapefile_multipoint_from_qgis(): - ds = mapnik.Shapefile(file='../data/shp/points/qgis_multi.shp') - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['id', 'name']) - eq_(ds.field_types(), ['int', 'str']) - eq_(len(list(ds.all_features())), 1) + ds = mapnik.Shapefile(file='./test/data/shp/points/qgis_multi.shp') + assert len(ds.fields()) == 2 + assert ds.fields(), ['id' == 'name'] + assert ds.field_types(), ['int' == 'str'] + assert len(list(ds.all_features())) == 1 # pointzm from arcinfo def test_shapefile_point_zm_from_arcgis(): - ds = mapnik.Shapefile(file='../data/shp/points/poi.shp') - eq_(len(ds.fields()), 7) - eq_(ds.fields(), - ['interst_id', - 'state_d', - 'cnty_name', - 'latitude', - 'longitude', - 'Name', - 'Website']) - eq_(ds.field_types(), ['str', 'str', - 'str', 'float', 'float', 'str', 'str']) - eq_(len(list(ds.all_features())), 17) + ds = mapnik.Shapefile(file='./test/data/shp/points/poi.shp') + assert len(ds.fields()) == 7 + assert ds.fields() == ['interst_id', + 'state_d', + 'cnty_name', + 'latitude', + 'longitude', + 'Name', + 'Website'] + assert ds.field_types() == ['str', 'str', 'str', 'float', 'float', 'str', 'str'] + assert len(list(ds.all_features())) == 17 # copy of the above with ogr2ogr that makes m record 14 instead of 18 def test_shapefile_point_zm_from_ogr(): - ds = mapnik.Shapefile(file='../data/shp/points/poi_ogr.shp') - eq_(len(ds.fields()), 7) - eq_(ds.fields(), - ['interst_id', - 'state_d', - 'cnty_name', - 'latitude', - 'longitude', - 'Name', - 'Website']) - eq_(ds.field_types(), ['str', 'str', - 'str', 'float', 'float', 'str', 'str']) - eq_(len(list(ds.all_features())), 17) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + ds = mapnik.Shapefile(file='./test/data/shp/points/poi_ogr.shp') + assert len(ds.fields()) == 7 + assert ds.fields(),['interst_id', + 'state_d', + 'cnty_name', + 'latitude', + 'longitude', + 'Name', + 'Website'] + assert ds.field_types() == ['str', 'str', 'str', 'float', 'float', 'str', 'str'] + assert len(list(ds.all_features())) == 17 From 67f7222c6cf1fe55da0a27d83e435dd2825be22e Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 8 Feb 2023 11:49:01 +0000 Subject: [PATCH 12/37] Unit tests - upgrade palette_test --- test/python_tests/palette_test.py | 59 +++++++++---------------------- 1 file changed, 16 insertions(+), 43 deletions(-) diff --git a/test/python_tests/palette_test.py b/test/python_tests/palette_test.py index 9913f81f2..849a6c3f1 100644 --- a/test/python_tests/palette_test.py +++ b/test/python_tests/palette_test.py @@ -1,23 +1,6 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os -import sys - -from nose.tools import eq_ - +import sys, os import mapnik -from .utilities import execution_path, run_all - -PYTHON3 = sys.version_info[0] == 3 - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - expected_64 = '[Palette 64 colors #494746 #c37631 #89827c #d1955c #7397b9 #fc9237 #a09f9c #fbc147 #9bb3ce #b7c9a1 #b5d29c #c4b9aa #cdc4a5 #d5c8a3 #c1d7aa #ccc4b6 #dbd19c #b2c4d5 #eae487 #c9c8c6 #e4db99 #c9dcb5 #dfd3ac #cbd2c2 #d6cdbc #dbd2b6 #c0ceda #ece597 #f7ef86 #d7d3c3 #dfcbc3 #d1d0cd #d1e2bf #d3dec1 #dbd3c4 #e6d8b6 #f4ef91 #d3d3cf #cad5de #ded7c9 #dfdbce #fcf993 #ffff8a #dbd9d7 #dbe7cd #d4dce2 #e4ded3 #ebe3c9 #e0e2e2 #f4edc3 #fdfcae #e9e5dc #f4edda #eeebe4 #fefdc5 #e7edf2 #edf4e5 #f2efe9 #f6ede7 #fefedd #f6f4f0 #f1f5f8 #fbfaf8 #ffffff]' expected_256 = '[Palette 256 colors #272727 #3c3c3c #484847 #564b41 #605243 #6a523e #555555 #785941 #5d5d5d #746856 #676767 #956740 #ba712e #787777 #cb752a #c27c3d #b68049 #dc8030 #df9e10 #878685 #e1a214 #928b82 #a88a70 #ea8834 #e7a81d #cb8d55 #909090 #94938c #e18f48 #f68d36 #6f94b7 #e1ab2e #8e959b #c79666 #999897 #ff9238 #ef9447 #a99a88 #f1b32c #919ca6 #a1a09f #f0b04b #8aa4bf #f8bc39 #b3ac8f #d1a67a #e3b857 #a8a8a7 #ffc345 #a2adb9 #afaeab #f9ab69 #afbba4 #c4c48a #b4b2af #dec177 #9ab2cf #a3bebb #d7b491 #b6cd9e #b5d29c #b9c8a2 #f1c969 #c5c79e #bbbab9 #cabdaa #a6bcd1 #cec4a7 #e7cc89 #dad98a #d5c9a3 #fabd8a #c1d7aa #cec5b4 #d1d1a5 #d9cf9f #c5c4c3 #d3c7b5 #ddd59d #b4c6d6 #d1cbb4 #d1c7ba #d7d1aa #e1c6ab #cbc7c2 #dbd0a9 #e8e58a #fee178 #d3cbba #dfd7a3 #d2cfb9 #c9ddb5 #d2cbbe #c3cbce #d7cbba #dcceb2 #dfd3aa #e5dd9a #dbd3b1 #ceccc6 #d7cbbe #d7cfba #dfc3be #dfd3ae #cbcbcb #cbd3c3 #d3cfc0 #e0d8aa #d7cfbe #dbd3b8 #ebe596 #dfd8b0 #c0ceda #f1ee89 #decfbc #d7cfc4 #d7d3c3 #d1d0cd #d2dfc0 #dbd3c3 #e7c7c3 #e7d7b3 #f2ed92 #d1e2bf #dad7c3 #fef383 #d3d3cf #dbd3c7 #e0d3c2 #dfd7c0 #ebe4a8 #dbd7c7 #dfd3c7 #f7f38f #c9d4de #dcdcc5 #dfd7c7 #e7d5c2 #d6d5d4 #faf78e #d7dfca #fbfb8a #fffb86 #dfd7cb #e5ddc0 #dad7d2 #ecd6c1 #cfd7de #e8d0cc #fbfb8e #fffb8a #eae3b8 #e3d7cd #dfdbce #fffb8e #ffff8a #f5efa6 #dae6cc #e3dbcf #edddc3 #dddbd6 #d5dbdf #ffff91 #e3dbd3 #fefc99 #e7dbd2 #eaddcd #e3dfd3 #ebd7d3 #dddddd #d4dee6 #e2dfd7 #fcdcc0 #e7dbd7 #e7dfd3 #ebe4cb #f4eeb8 #e3dfdb #e7dfd7 #ebded5 #e7e3d7 #fefea6 #e1ecd6 #ece5d3 #e7e3db #dee3e5 #ebe3db #efdfdb #efe3d8 #f4efc9 #e6ecdb #ebe3df #ebe7db #f0ecd3 #e5e6e5 #efe7da #ebe7df #efe3df #fefeb8 #dfe7ef #ebe7e3 #edebde #efe7e0 #e8efe0 #e7f3df #ebebe3 #e7ebe8 #f5edd9 #efebe3 #e3ebf1 #e9efe7 #ebebea #efebe7 #f0efe2 #ecf3e5 #fefdc9 #efefe7 #f3efe7 #f5f3e1 #f2efe9 #e9eef4 #ffeddf #efefef #f3efeb #f3f3eb #f0f7eb #fbf7e1 #fefed8 #f3f3ef #f7f3eb #eef3f7 #f7f7ea #f3f3f3 #f3f7ef #f7f3ef #f3f3f7 #f7f3f3 #f7f7ef #fffee3 #f3f7f7 #f7f7f3 #fcf7ee #f7f7f7 #f7fbf4 #f5f7fb #fbf7f6 #fffeef #f7fbfb #fbfbf7 #fbfbfb #fbfbff #fbfffb #fffbfb #fbffff #fffffb #ffffff]' @@ -26,31 +9,28 @@ def setup(): def test_reading_palettes(): - with open('../data/palettes/palette64.act', 'rb') as act: + with open('./test/data/palettes/palette64.act', 'rb') as act: palette = mapnik.Palette(act.read(), 'act') - eq_(palette.to_string(), expected_64) - with open('../data/palettes/palette256.act', 'rb') as act: + assert palette.to_string() == expected_64 + with open('./test/data/palettes/palette256.act', 'rb') as act: palette = mapnik.Palette(act.read(), 'act') - eq_(palette.to_string(), expected_256) - if PYTHON3: - palette = mapnik.Palette(b'\xff\x00\xff\xff\xff\xff', 'rgb') - else: - palette = mapnik.Palette('\xff\x00\xff\xff\xff\xff', 'rgb') - eq_(palette.to_string(), expected_rgb) + assert palette.to_string() == expected_256 + palette = mapnik.Palette(b'\xff\x00\xff\xff\xff\xff', 'rgb') + assert palette.to_string() == expected_rgb if 'shape' in mapnik.DatasourceCache.plugin_names(): def test_render_with_palette(): m = mapnik.Map(600, 400) - mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') + mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') m.zoom_all() im = mapnik.Image(m.width, m.height) mapnik.render(m, im) - with open('../data/palettes/palette256.act', 'rb') as act: + with open('./test/data/palettes/palette256.act', 'rb') as act: palette = mapnik.Palette(act.read(), 'act') # test saving directly to filesystem im.save('/tmp/mapnik-palette-test.png', 'png', palette) - expected = './images/support/mapnik-palette-test.png' + expected = './test/python_tests/images/support/mapnik-palette-test.png' if os.environ.get('UPDATE'): im.save(expected, "png", palette) @@ -58,17 +38,10 @@ def test_render_with_palette(): with open('/tmp/mapnik-palette-test2.png', 'wb') as f: f.write(im.tostring('png', palette)) # compare the two methods - eq_(mapnik.Image.open('/tmp/mapnik-palette-test.png').tostring('png32'), - mapnik.Image.open( - '/tmp/mapnik-palette-test2.png').tostring('png32'), - '%s not eq to %s' % ('/tmp/mapnik-palette-test.png', - '/tmp/mapnik-palette-test2.png')) + im1 = mapnik.Image.open('/tmp/mapnik-palette-test.png') + im2 = mapnik.Image.open('/tmp/mapnik-palette-test2.png') + assert im1.tostring('png32') == im1.tostring('png32'),'%s not eq to %s' % ('/tmp/mapnik-palette-test.png', + '/tmp/mapnik-palette-test2.png') # compare to expected - eq_(mapnik.Image.open('/tmp/mapnik-palette-test.png').tostring('png32'), - mapnik.Image.open(expected).tostring('png32'), - '%s not eq to %s' % ('/tmp/mapnik-palette-test.png', - expected)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im1.tostring('png32') == mapnik.Image.open(expected).tostring('png32'), '%s not eq to %s' % ('/tmp/mapnik-palette-test.png', + expected) From 0697787e1a0d533633a75da54ea4dfd8eb6fd674 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 8 Feb 2023 11:49:43 +0000 Subject: [PATCH 13/37] Unit tests - upgrade `printing` module to use `pypdf` package + update pdf printing test --- mapnik/printing/__init__.py | 63 +++++++++--------- .../images/pycairo/pdf-printing-expected.pdf | Bin 81792 -> 66156 bytes test/python_tests/pdf_printing_test.py | 62 +++++++---------- 3 files changed, 53 insertions(+), 72 deletions(-) diff --git a/mapnik/printing/__init__.py b/mapnik/printing/__init__.py index 023f1380d..0af163145 100644 --- a/mapnik/printing/__init__.py +++ b/mapnik/printing/__init__.py @@ -2,11 +2,8 @@ """Mapnik classes to assist in creating printable maps.""" -from __future__ import absolute_import, print_function - import logging import math - from mapnik import Box2d, Coord, Geometry, Layer, Map, Projection, Style, render from mapnik.printing.conversions import m2pt, m2px from mapnik.printing.formats import pagesizes @@ -25,12 +22,12 @@ HAS_PANGOCAIRO_MODULE = False try: - from PyPDF2 import PdfFileReader, PdfFileWriter - from PyPDF2.generic import (ArrayObject, DecodedStreamObject, DictionaryObject, FloatObject, NameObject, - NumberObject, TextStringObject) - HAS_PYPDF2 = True + from pypdf import PdfReader, PdfWriter + from pypdf.generic import (ArrayObject, DecodedStreamObject, DictionaryObject, FloatObject, NameObject, + NumberObject, TextStringObject) + HAS_PYPDF = True except ImportError: - HAS_PYPDF2 = False + HAS_PYPDF = False """ Style of centering to use with the map. @@ -90,7 +87,7 @@ def __init__(self, Args: pagesize: tuple of page size in meters, see predefined sizes in mapnik.formats module margin: page margin in meters - box: the box to render the map into. Must be within page area, margin excluded. + box: the box to render the map into. Must be within page area, margin excluded. This should be a Mapnik Box2d object. Default is the full page without margin. percent_box: similar to box argument but specified as a percent (0->1) of the full page size. If both box and percent_box are specified percent_box will be used. @@ -104,7 +101,7 @@ def __init__(self, be a value from the mapnik.utils.centering class. The default is to center on the maps constrained axis. Typically this will be horizontal for portrait pages and vertical for landscape pages. is_latlon: whether the map is in lat lon degrees or not. - use_ocg_layers: create OCG layers in the PDF, requires PyPDF2 + use_ocg_layers: create OCG layers in the PDF, requires pypdf font_name: the font name used each time text is written (e.g., legend titles, representative fraction, etc.) """ self._pagesize = pagesize @@ -563,7 +560,7 @@ def render_scale(self, m, ctx=None, width=0.05, num_divisions=3, bar_size=8.0, w Args: m: the Map object to render the scale for - ctx: A cairo context to render the scale into. If this is None, we create a context and find out + ctx: A cairo context to render the scale into. If this is None, we create a context and find out the best location for the scale bar width: the width of area available for rendering the scale bar (in meters) num_divisions: the number of divisions for the scale bar @@ -737,7 +734,7 @@ def render_graticule_on_map(self, m, dec_degrees=True, grid_layer_name="Graticul # renders the vertical graticule axes self._render_graticule_axes_and_text( - m, + m, p2, latlon_bounds, latlon_buffer, @@ -1119,7 +1116,7 @@ def convert_pdf_pages_to_layers(self, filename, layer_names=None, reverse_all_bu Takes a multi pages PDF as input and converts each page to a layer in a single page PDF. Note: - requires PyPDF2 to be available + requires pypdf to be available Args: layer_names should be a sequence of the user visible names of the layers, if not given @@ -1128,17 +1125,17 @@ def convert_pdf_pages_to_layers(self, filename, layer_names=None, reverse_all_bu if output_name is not provided a temporary file will be used for the conversion which will then be copied back over the source file. """ - if not HAS_PYPDF2: - raise RuntimeError("PyPDF2 not available; PyPDF2 required to convert pdf pages to layers") + if not HAS_PYPDF: + raise RuntimeError("pypdf not available; pypdf required to convert pdf pages to layers") with open(filename, "rb+") as f: - file_reader = PdfFileReader(f) - file_writer = PdfFileWriter() + file_reader = PdfReader(f) + file_writer = PdfWriter() - template_page_size = file_reader.pages[0].mediaBox - output_pdf = file_writer.addBlankPage( - width=template_page_size.getWidth(), - height=template_page_size.getHeight()) + template_page_size = file_reader.pages[0].mediabox + output_pdf = file_writer.add_blank_page( + width=template_page_size.width, + height=template_page_size.height) content_key = NameObject('/Contents') output_pdf[content_key] = ArrayObject() @@ -1149,15 +1146,15 @@ def convert_pdf_pages_to_layers(self, filename, layer_names=None, reverse_all_bu (properties, ocgs) = self._make_ocg_layers(file_reader, file_writer, output_pdf, layer_names) properties_key = NameObject('/Properties') - output_pdf[resource_key][properties_key] = file_writer._addObject(properties) + output_pdf[resource_key][properties_key] = file_writer._add_object(properties) ocproperties = DictionaryObject() ocproperties[NameObject('/OCGs')] = ocgs default_view = self._get_pdf_default_view(ocgs, reverse_all_but_last) - ocproperties[NameObject('/D')] = file_writer._addObject(default_view) + ocproperties[NameObject('/D')] = file_writer._add_object(default_view) - file_writer._root_object[NameObject('/OCProperties')] = file_writer._addObject(ocproperties) + file_writer._root_object[NameObject('/OCProperties')] = file_writer._add_object(ocproperties) f.seek(0) file_writer.write(f) @@ -1189,7 +1186,7 @@ def _make_ocg_layers(self, file_reader, file_writer, output_pdf, layer_names=Non page[NameObject( '/Contents')] = ArrayObject((ocgs_start, page['/Contents'], ocg_end)) - output_pdf.mergePage(page) + output_pdf.merge_page(page) ocg = DictionaryObject() ocg[NameObject('/Type')] = NameObject('/OCG') @@ -1199,7 +1196,7 @@ def _make_ocg_layers(self, file_reader, file_writer, output_pdf, layer_names=Non else: ocg[NameObject('/Name')] = TextStringObject('Layer %d' % (idx + 1)) - indirect_ocg = file_writer._addObject(ocg) + indirect_ocg = file_writer._add_object(ocg) properties[ocg_name] = indirect_ocg ocgs.append(indirect_ocg) @@ -1238,20 +1235,20 @@ def add_geospatial_pdf_header(self, m, filename, epsg=None, wkt=None): The epsg code or the wkt text of the projection must be provided. Must be called *after* the page has had .finish() called. """ - if not HAS_PYPDF2: - raise RuntimeError("PyPDF2 not available; PyPDF2 required to add geospatial header to PDF") + if not HAS_PYPDF: + raise RuntimeError("pypdf not available; pypdf required to add geospatial header to PDF") if not any((epsg,wkt)): raise RuntimeError("EPSG or WKT required to add geospatial header to PDF") with open(filename, "rb+") as f: - file_reader = PdfFileReader(f) - file_writer = PdfFileWriter() + file_reader = PdfReader(f) + file_writer = PdfWriter() # preserve OCProperties at document root if we have one - if file_reader.trailer['/Root'].has_key(NameObject('/OCProperties')): + if NameObject('/OCProperties') in file_reader.trailer['/Root']: file_writer._root_object[NameObject('/OCProperties')] = file_reader.trailer[ - '/Root'].getObject()[NameObject('/OCProperties')] + '/Root'].get_object()[NameObject('/OCProperties')] for page in file_reader.pages: gcs = DictionaryObject() @@ -1265,7 +1262,7 @@ def add_geospatial_pdf_header(self, m, filename, epsg=None, wkt=None): measure = self._get_pdf_measure(m, gcs) page[NameObject('/VP')] = self._get_pdf_vp(measure) - file_writer.addPage(page) + file_writer.add_page(page) f.seek(0) file_writer.write(f) diff --git a/test/python_tests/images/pycairo/pdf-printing-expected.pdf b/test/python_tests/images/pycairo/pdf-printing-expected.pdf index e0dedea5f2cfd1e2b0f9f59a7bb916e78dde4a49..bf300ba05c99365597bb0d385fb140919b952404 100644 GIT binary patch literal 66156 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

qjK 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 z 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 Date: Wed, 8 Feb 2023 12:17:21 +0000 Subject: [PATCH 14/37] Unit tests - upgrade parameters_test --- test/python_tests/parameters_test.py | 55 +++++++++------------------- 1 file changed, 18 insertions(+), 37 deletions(-) diff --git a/test/python_tests/parameters_test.py b/test/python_tests/parameters_test.py index f6e25b848..ca23c47fc 100644 --- a/test/python_tests/parameters_test.py +++ b/test/python_tests/parameters_test.py @@ -1,71 +1,52 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os import sys - -from nose.tools import eq_ - import mapnik -from .utilities import execution_path, run_all - - -def setup(): - os.chdir(execution_path('.')) - - def test_parameter_null(): p = mapnik.Parameter('key', None) - eq_(p[0], 'key') - eq_(p[1], None) + assert p[0] == 'key' + assert p[1] == None def test_parameter_string(): p = mapnik.Parameter('key', 'value') - eq_(p[0], 'key') - eq_(p[1], 'value') + assert p[0] == 'key' + assert p[1] == 'value' def test_parameter_unicode(): p = mapnik.Parameter('key', u'value') - eq_(p[0], 'key') - eq_(p[1], u'value') + assert p[0] == 'key' + assert p[1] == u'value' def test_parameter_integer(): p = mapnik.Parameter('int', sys.maxsize) - eq_(p[0], 'int') - eq_(p[1], sys.maxsize) + assert p[0] == 'int' + assert p[1] == sys.maxsize def test_parameter_double(): p = mapnik.Parameter('double', float(sys.maxsize)) - eq_(p[0], 'double') - eq_(p[1], float(sys.maxsize)) + assert p[0] == 'double' + assert p[1] == float(sys.maxsize) def test_parameter_boolean(): p = mapnik.Parameter('boolean', True) - eq_(p[0], 'boolean') - eq_(p[1], True) - eq_(bool(p[1]), True) + assert p[0] == 'boolean' + assert p[1] == True + assert bool(p[1]) == True def test_parameters(): params = mapnik.Parameters() p = mapnik.Parameter('float', 1.0777) - eq_(p[0], 'float') - eq_(p[1], 1.0777) + assert p[0] == 'float' + assert p[1] == 1.0777 params.append(p) - eq_(params[0][0], 'float') - eq_(params[0][1], 1.0777) - - eq_(params.get('float'), 1.0777) - + assert params[0][0] == 'float' + assert params[0][1] == 1.0777 -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert params.get('float') == 1.0777 From 494752da1ca0627e3cf5f6b17389200ecfb34575 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 8 Feb 2023 16:26:54 +0000 Subject: [PATCH 15/37] Unit tests - upgrade postgis_test --- test/python_tests/postgis_test.py | 952 +++++++++++++++--------------- 1 file changed, 464 insertions(+), 488 deletions(-) diff --git a/test/python_tests/postgis_test.py b/test/python_tests/postgis_test.py index c3d5f8a43..0549c94c1 100644 --- a/test/python_tests/postgis_test.py +++ b/test/python_tests/postgis_test.py @@ -1,31 +1,14 @@ -#!/usr/bin/env python import atexit import os import sys import threading from subprocess import PIPE, Popen - -from nose.tools import eq_, raises - import mapnik - -from .utilities import execution_path, run_all - -PYTHON3 = sys.version_info[0] == 3 -if PYTHON3: - long = int - +import pytest MAPNIK_TEST_DBNAME = 'mapnik-tmp-postgis-test-db' POSTGIS_TEMPLATE_DBNAME = 'template_postgis' -SHAPEFILE = os.path.join(execution_path('.'), '../data/shp/world_merc.shp') - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - +SHAPEFILE = './test/data/shp/world_merc.shp' def call(cmd, silent=False): stdin, stderr = Popen(cmd, shell=True, stdout=PIPE, @@ -305,23 +288,23 @@ def test_feature(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='world_merc') fs = ds.featureset() feature = fs.next() - eq_(feature['gid'], 1) - eq_(feature['fips'], u'AC') - eq_(feature['iso2'], u'AG') - eq_(feature['iso3'], u'ATG') - eq_(feature['un'], 28) - eq_(feature['name'], u'Antigua and Barbuda') - eq_(feature['area'], 44) - eq_(feature['pop2005'], 83039) - eq_(feature['region'], 19) - eq_(feature['subregion'], 29) - eq_(feature['lon'], -61.783) - eq_(feature['lat'], 17.078) + assert feature['gid'] == 1 + assert feature['fips'] == u'AC' + assert feature['iso2'] == u'AG' + assert feature['iso3'] == u'ATG' + assert feature['un'] == 28 + assert feature['name'] == u'Antigua and Barbuda' + assert feature['area'] == 44 + assert feature['pop2005'] == 83039 + assert feature['region'] == 19 + assert feature['subregion'] == 29 + assert feature['lon'] == -61.783 + assert feature['lat'] == 17.078 meta = ds.describe() - eq_(meta['srid'], 3857) - eq_(meta.get('key_field'), None) - eq_(meta['encoding'], u'UTF8') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Polygon) + assert meta['srid'] == 3857 + assert meta.get('key_field') == None + assert meta['encoding'] == u'UTF8' + assert meta['geometry_type'] == mapnik.DataGeometryType.Polygon def test_subquery(): ds = mapnik.PostGIS( @@ -329,37 +312,37 @@ def test_subquery(): table='(select * from world_merc) as w') fs = ds.featureset() feature = fs.next() - eq_(feature['gid'], 1) - eq_(feature['fips'], u'AC') - eq_(feature['iso2'], u'AG') - eq_(feature['iso3'], u'ATG') - eq_(feature['un'], 28) - eq_(feature['name'], u'Antigua and Barbuda') - eq_(feature['area'], 44) - eq_(feature['pop2005'], 83039) - eq_(feature['region'], 19) - eq_(feature['subregion'], 29) - eq_(feature['lon'], -61.783) - eq_(feature['lat'], 17.078) + assert feature['gid'] == 1 + assert feature['fips'] == u'AC' + assert feature['iso2'] == u'AG' + assert feature['iso3'] == u'ATG' + assert feature['un'] == 28 + assert feature['name'] == u'Antigua and Barbuda' + assert feature['area'] == 44 + assert feature['pop2005'] == 83039 + assert feature['region'] == 19 + assert feature['subregion'] == 29 + assert feature['lon'] == -61.783 + assert feature['lat'] == 17.078 meta = ds.describe() - eq_(meta['srid'], 3857) - eq_(meta.get('key_field'), None) - eq_(meta['encoding'], u'UTF8') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Polygon) + assert meta['srid'] == 3857 + assert meta.get('key_field') == None + assert meta['encoding'] == u'UTF8' + assert meta['geometry_type'] == mapnik.DataGeometryType.Polygon ds = mapnik.PostGIS( dbname=MAPNIK_TEST_DBNAME, table='(select gid,geom,fips as _fips from world_merc) as w') fs = ds.featureset() feature = fs.next() - eq_(feature['gid'], 1) - eq_(feature['_fips'], u'AC') - eq_(len(feature), 2) + assert feature['gid'] == 1 + assert feature['_fips'] == u'AC' + assert len(feature) == 2 meta = ds.describe() - eq_(meta['srid'], 3857) - eq_(meta.get('key_field'), None) - eq_(meta['encoding'], u'UTF8') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Polygon) + assert meta['srid'] == 3857 + assert meta.get('key_field') == None + assert meta['encoding'] == u'UTF8' + assert meta['geometry_type'] == mapnik.DataGeometryType.Polygon def test_bad_connection(): try: @@ -374,60 +357,62 @@ def test_bad_connection(): def test_empty_db(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='empty') - fs = ds.featureset() + fs = ds.features(mapnik.Query(mapnik.Box2d(-180,-90,180,90))) feature = None try: feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), None) - eq_(meta['encoding'], u'UTF8') - eq_(meta['geometry_type'], None) + assert meta['srid'] == -1 + assert meta.get('key_field') == None + assert meta['encoding'] == u'UTF8' + assert meta['geometry_type'] == None def test_manual_srid(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, srid=99, table='empty') - fs = ds.featureset() + fs = ds.features(mapnik.Query(mapnik.Box2d(-180,-90,180,90))) feature = None try: feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None meta = ds.describe() - eq_(meta['srid'], 99) - eq_(meta.get('key_field'), None) - eq_(meta['encoding'], u'UTF8') - eq_(meta['geometry_type'], None) + assert meta['srid'] == 99 + assert meta.get('key_field') == None + assert meta['encoding'] == u'UTF8' + assert meta['geometry_type'] == None def test_geometry_detection(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test', geometry_field='geom') meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Collection) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Collection # will fail with postgis 2.0 because it automatically adds a geometry_columns entry # ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME,table='test', # geometry_field='geom', # row_limit=1) - # eq_(ds.describe()['geometry_type'],mapnik.DataGeometryType.Point) + # assert ds.describe()['geometry_type'] == mapnik.DataGeometryType.Point + - @raises(RuntimeError) def test_that_nonexistant_query_field_throws(**kwargs): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='empty') - eq_(len(ds.fields()), 1) - eq_(ds.fields(), ['key']) - eq_(ds.field_types(), ['int']) + assert len(ds.fields()) == 1 + assert ds.fields() == ['key'] + assert ds.field_types() == ['int'] query = mapnik.Query(ds.envelope()) + for fld in ds.fields(): query.add_property_name(fld) - # also add an invalid one, triggering throw - query.add_property_name('bogus') - ds.features(query) + # also add an invalid one, triggering throw + query.add_property_name('bogus') + with pytest.raises(RuntimeError): + ds.features(query) def test_auto_detection_of_unique_feature_id_32_bit(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test2', @@ -435,25 +420,25 @@ def test_auto_detection_of_unique_feature_id_32_bit(): autodetect_key_field=True) fs = ds.featureset() f = fs.next() - eq_(len(ds.fields()),len(f.attributes)) - eq_(f['manual_id'], 0) - eq_(fs.next()['manual_id'], 1) - eq_(fs.next()['manual_id'], 1000) - eq_(fs.next()['manual_id'], -1000) - eq_(fs.next()['manual_id'], 2147483647) - eq_(fs.next()['manual_id'], -2147483648) + assert len(ds.fields()) == len(f.attributes) + assert f['manual_id'] == 0 + assert fs.next()['manual_id'] == 1 + assert fs.next()['manual_id'] == 1000 + assert fs.next()['manual_id'] == -1000 + assert fs.next()['manual_id'] == 2147483647 + assert fs.next()['manual_id'] == -2147483648 fs = ds.featureset() - eq_(fs.next().id(), 0) - eq_(fs.next().id(), 1) - eq_(fs.next().id(), 1000) - eq_(fs.next().id(), -1000) - eq_(fs.next().id(), 2147483647) - eq_(fs.next().id(), -2147483648) + assert fs.next().id() == 0 + assert fs.next().id() == 1 + assert fs.next().id() == 1000 + assert fs.next().id() == -1000 + assert fs.next().id() == 2147483647 + assert fs.next().id() == -2147483648 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), u'manual_id') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == u'manual_id' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_auto_detection_of_unique_feature_id_32_bit_no_attribute(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test2', @@ -462,19 +447,19 @@ def test_auto_detection_of_unique_feature_id_32_bit_no_attribute(): key_field_as_attribute=False) fs = ds.featureset() f = fs.next() - eq_(len(ds.fields()),len(f.attributes)) - eq_(len(ds.fields()),0) - eq_(len(f.attributes),0) - eq_(f.id(), 0) - eq_(fs.next().id(), 1) - eq_(fs.next().id(), 1000) - eq_(fs.next().id(), -1000) - eq_(fs.next().id(), 2147483647) - eq_(fs.next().id(), -2147483648) + assert len(ds.fields()) == len(f.attributes) + assert len(ds.fields()) == 0 + assert len(f.attributes) == 0 + assert f.id() == 0 + assert fs.next().id() == 1 + assert fs.next().id() == 1000 + assert fs.next().id() == -1000 + assert fs.next().id() == 2147483647 + assert fs.next().id() == -2147483648 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), u'manual_id') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == u'manual_id' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_auto_detection_will_fail_since_no_primary_key(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test3', @@ -482,35 +467,36 @@ def test_auto_detection_will_fail_since_no_primary_key(): autodetect_key_field=False) fs = ds.featureset() feat = fs.next() - eq_(feat['manual_id'], 0) - eq_(feat['non_id'],9223372036854775807) - eq_(fs.next()['manual_id'], 1) - eq_(fs.next()['manual_id'], 1000) - eq_(fs.next()['manual_id'], -1000) - eq_(fs.next()['manual_id'], 2147483647) - eq_(fs.next()['manual_id'], -2147483648) + assert feat['manual_id'] == 0 + assert feat['non_id'] == 9223372036854775807 + assert fs.next()['manual_id'] == 1 + assert fs.next()['manual_id'] == 1000 + assert fs.next()['manual_id'] == -1000 + assert fs.next()['manual_id'] == 2147483647 + assert fs.next()['manual_id'] == -2147483648 # since no valid primary key will be detected the fallback # is auto-incrementing counter fs = ds.featureset() - eq_(fs.next().id(), 1) - eq_(fs.next().id(), 2) - eq_(fs.next().id(), 3) - eq_(fs.next().id(), 4) - eq_(fs.next().id(), 5) - eq_(fs.next().id(), 6) + assert fs.next().id() == 1 + assert fs.next().id() == 2 + assert fs.next().id() == 3 + assert fs.next().id() == 4 + assert fs.next().id() == 5 + assert fs.next().id() == 6 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Point + - @raises(RuntimeError) def test_auto_detection_will_fail_and_should_throw(): - ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test3', - geometry_field='geom', - autodetect_key_field=True) - ds.featureset() + with pytest.raises(RuntimeError): + ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test3', + geometry_field='geom', + autodetect_key_field=True) + ds.featureset() def test_auto_detection_of_unique_feature_id_64_bit(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test4', @@ -518,26 +504,26 @@ def test_auto_detection_of_unique_feature_id_64_bit(): autodetect_key_field=True) fs = ds.featureset() f = fs.next() - eq_(len(ds.fields()),len(f.attributes)) - eq_(f['manual_id'], 0) - eq_(fs.next()['manual_id'], 1) - eq_(fs.next()['manual_id'], 1000) - eq_(fs.next()['manual_id'], -1000) - eq_(fs.next()['manual_id'], 2147483647) - eq_(fs.next()['manual_id'], -2147483648) + assert len(ds.fields()) == len(f.attributes) + assert f['manual_id'] == 0 + assert fs.next()['manual_id'] == 1 + assert fs.next()['manual_id'] == 1000 + assert fs.next()['manual_id'] == -1000 + assert fs.next()['manual_id'] == 2147483647 + assert fs.next()['manual_id'] == -2147483648 fs = ds.featureset() - eq_(fs.next().id(), 0) - eq_(fs.next().id(), 1) - eq_(fs.next().id(), 1000) - eq_(fs.next().id(), -1000) - eq_(fs.next().id(), 2147483647) - eq_(fs.next().id(), -2147483648) + assert fs.next().id() == 0 + assert fs.next().id() == 1 + assert fs.next().id() == 1000 + assert fs.next().id() == -1000 + assert fs.next().id() == 2147483647 + assert fs.next().id() == -2147483648 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), u'manual_id') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == u'manual_id' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_disabled_auto_detection_and_subquery(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''(select geom, 'a'::varchar as name from test2) as t''', @@ -545,28 +531,28 @@ def test_disabled_auto_detection_and_subquery(): autodetect_key_field=False) fs = ds.featureset() feat = fs.next() - eq_(feat.id(), 1) - eq_(feat['name'], 'a') + assert feat.id() == 1 + assert feat['name'] == 'a' feat = fs.next() - eq_(feat.id(), 2) - eq_(feat['name'], 'a') + assert feat.id() == 2 + assert feat['name'] == 'a' feat = fs.next() - eq_(feat.id(), 3) - eq_(feat['name'], 'a') + assert feat.id() == 3 + assert feat['name'] == 'a' feat = fs.next() - eq_(feat.id(), 4) - eq_(feat['name'], 'a') + assert feat.id() == 4 + assert feat['name'] == 'a' feat = fs.next() - eq_(feat.id(), 5) - eq_(feat['name'], 'a') + assert feat.id() == 5 + assert feat['name'] == 'a' feat = fs.next() - eq_(feat.id(), 6) - eq_(feat['name'], 'a') + assert feat.id() == 6 + assert feat['name'] == 'a' meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_auto_detection_and_subquery_including_key(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''(select geom, manual_id from test2) as t''', @@ -574,44 +560,47 @@ def test_auto_detection_and_subquery_including_key(): autodetect_key_field=True) fs = ds.featureset() f = fs.next() - eq_(len(ds.fields()),len(f.attributes)) - eq_(f['manual_id'], 0) - eq_(fs.next()['manual_id'], 1) - eq_(fs.next()['manual_id'], 1000) - eq_(fs.next()['manual_id'], -1000) - eq_(fs.next()['manual_id'], 2147483647) - eq_(fs.next()['manual_id'], -2147483648) + assert len(ds.fields()) == len(f.attributes) + assert f['manual_id'] == 0 + assert fs.next()['manual_id'] == 1 + assert fs.next()['manual_id'] == 1000 + assert fs.next()['manual_id'] == -1000 + assert fs.next()['manual_id'] == 2147483647 + assert fs.next()['manual_id'] == -2147483648 fs = ds.featureset() - eq_(fs.next().id(), 0) - eq_(fs.next().id(), 1) - eq_(fs.next().id(), 1000) - eq_(fs.next().id(), -1000) - eq_(fs.next().id(), 2147483647) - eq_(fs.next().id(), -2147483648) + assert fs.next().id() == 0 + assert fs.next().id() == 1 + assert fs.next().id() == 1000 + assert fs.next().id() == -1000 + assert fs.next().id() == 2147483647 + assert fs.next().id() == -2147483648 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), u'manual_id') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == u'manual_id' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point + - @raises(RuntimeError) def test_auto_detection_of_invalid_numeric_primary_key(): - mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''(select geom, manual_id::numeric from test2) as t''', - geometry_field='geom', - autodetect_key_field=True) + with pytest.raises(RuntimeError): + mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''(select geom, manual_id::numeric from test2) as t''', + geometry_field='geom', + autodetect_key_field=True) + - @raises(RuntimeError) def test_auto_detection_of_invalid_multiple_keys(): - mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''test6''', - geometry_field='geom', - autodetect_key_field=True) + with pytest.raises(RuntimeError): + mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''test6''', + geometry_field='geom', + autodetect_key_field=True) + - @raises(RuntimeError) def test_auto_detection_of_invalid_multiple_keys_subquery(): - mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''(select first_id,second_id,geom from test6) as t''', - geometry_field='geom', - autodetect_key_field=True) + with pytest.raises(RuntimeError): + mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='''(select first_id,second_id,geom from test6) as t''', + geometry_field='geom', + autodetect_key_field=True) def test_manually_specified_feature_id_field(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test4', @@ -620,43 +609,43 @@ def test_manually_specified_feature_id_field(): autodetect_key_field=True) fs = ds.featureset() f = fs.next() - eq_(len(ds.fields()),len(f.attributes)) - eq_(f['manual_id'], 0) - eq_(fs.next()['manual_id'], 1) - eq_(fs.next()['manual_id'], 1000) - eq_(fs.next()['manual_id'], -1000) - eq_(fs.next()['manual_id'], 2147483647) - eq_(fs.next()['manual_id'], -2147483648) + assert len(ds.fields()) == len(f.attributes) + assert f['manual_id'] == 0 + assert fs.next()['manual_id'] == 1 + assert fs.next()['manual_id'] == 1000 + assert fs.next()['manual_id'] == -1000 + assert fs.next()['manual_id'] == 2147483647 + assert fs.next()['manual_id'] == -2147483648 fs = ds.featureset() - eq_(fs.next().id(), 0) - eq_(fs.next().id(), 1) - eq_(fs.next().id(), 1000) - eq_(fs.next().id(), -1000) - eq_(fs.next().id(), 2147483647) - eq_(fs.next().id(), -2147483648) + assert fs.next().id() == 0 + assert fs.next().id() == 1 + assert fs.next().id() == 1000 + assert fs.next().id() == -1000 + assert fs.next().id() == 2147483647 + assert fs.next().id() == -2147483648 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), u'manual_id') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == u'manual_id' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_numeric_type_feature_id_field(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test5', geometry_field='geom', autodetect_key_field=False) fs = ds.featureset() - eq_(fs.next()['manual_id'], -1) - eq_(fs.next()['manual_id'], 1) + assert fs.next()['manual_id'] == -1 + assert fs.next()['manual_id'] == 1 fs = ds.featureset() - eq_(fs.next().id(), 1) - eq_(fs.next().id(), 2) + assert fs.next().id() == 1 + assert fs.next().id() == 2 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_querying_table_with_mixed_case(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='"tableWithMixedCase"', @@ -664,12 +653,12 @@ def test_querying_table_with_mixed_case(): autodetect_key_field=True) fs = ds.featureset() for id in range(1, 5): - eq_(fs.next().id(), id) + assert fs.next().id() == id meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), u'gid') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == -1 + assert meta.get('key_field') == u'gid' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_querying_subquery_with_mixed_case(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='(SeLeCt * FrOm "tableWithMixedCase") as MixedCaseQuery', @@ -677,12 +666,12 @@ def test_querying_subquery_with_mixed_case(): autodetect_key_field=True) fs = ds.featureset() for id in range(1, 5): - eq_(fs.next().id(), id) + assert fs.next().id() == id meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), u'gid') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == -1 + assert meta.get('key_field') == u'gid' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_bbox_token_in_subquery1(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table=''' @@ -691,12 +680,12 @@ def test_bbox_token_in_subquery1(): autodetect_key_field=True) fs = ds.featureset() for id in range(1, 5): - eq_(fs.next().id(), id) + assert fs.next().id() == id meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), u'gid') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == -1 + assert meta.get('key_field') == u'gid' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_bbox_token_in_subquery2(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table=''' @@ -705,23 +694,23 @@ def test_bbox_token_in_subquery2(): autodetect_key_field=True) fs = ds.featureset() for id in range(1, 5): - eq_(fs.next().id(), id) + assert fs.next().id() == id meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), u'gid') - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == -1 + assert meta.get('key_field') == u'gid' + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_empty_geom(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test7', geometry_field='geom') fs = ds.featureset() - eq_(fs.next()['gid'], 1) + assert fs.next()['gid'] == 1 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Collection) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Collection def create_ds(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, @@ -729,12 +718,12 @@ def create_ds(): max_size=20, geometry_field='geom') fs = list(ds.all_features()) - eq_(len(fs), 8) + assert len(fs) == 8 meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Collection) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Collection def test_threaded_create(NUM_THREADS=100): # run one to start before thread loop @@ -747,7 +736,7 @@ def test_threaded_create(NUM_THREADS=100): t.start() t.join() runs += 1 - eq_(runs, NUM_THREADS) + assert runs == NUM_THREADS def create_ds_and_error(): try: @@ -756,7 +745,7 @@ def create_ds_and_error(): max_size=20) ds.all_features() except Exception as e: - eq_('in executeQuery' in str(e), True) + assert 'in executeQuery' in str(e) def test_threaded_create2(NUM_THREADS=10): for i in range(NUM_THREADS): @@ -768,23 +757,23 @@ def test_that_64bit_int_fields_work(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test8', geometry_field='geom') - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['gid', 'int_field']) - eq_(ds.field_types(), ['int', 'int']) + assert len(ds.fields()) == 2 + assert ds.fields(), ['gid' == 'int_field'] + assert ds.field_types(), ['int' == 'int'] fs = ds.featureset() feat = fs.next() - eq_(feat.id(), 1) - eq_(feat['gid'], 1) - eq_(feat['int_field'], 2147483648) + assert feat.id() == 1 + assert feat['gid'] == 1 + assert feat['int_field'] == 2147483648 feat = fs.next() - eq_(feat.id(), 2) - eq_(feat['gid'], 2) - eq_(feat['int_field'], 922337203685477580) + assert feat.id() == 2 + assert feat['gid'] == 2 + assert feat['int_field'] == 922337203685477580 meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == -1 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_persist_connection_off(): # NOTE: max_size should be equal or greater than @@ -800,11 +789,11 @@ def test_persist_connection_off(): table='(select ST_MakePoint(0,0) as g, pg_backend_pid() as p, 1 as v) as w', geometry_field='g') fs = ds.featureset() - eq_(fs.next()['v'], 1) + assert fs.next()['v'] == 1 meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == -1 + assert meta['geometry_type'] == mapnik.DataGeometryType.Point def test_null_comparision(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test9', @@ -813,51 +802,51 @@ def test_null_comparision(): feat = fs.next() meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) - - eq_(feat['gid'], 1) - eq_(feat['name'], 'name') - eq_(mapnik.Expression("[name] = 'name'").evaluate(feat), True) - eq_(mapnik.Expression("[name] = ''").evaluate(feat), False) - eq_(mapnik.Expression("[name] = null").evaluate(feat), False) - eq_(mapnik.Expression("[name] = true").evaluate(feat), False) - eq_(mapnik.Expression("[name] = false").evaluate(feat), False) - eq_(mapnik.Expression("[name] != 'name'").evaluate(feat), False) - eq_(mapnik.Expression("[name] != ''").evaluate(feat), True) - eq_(mapnik.Expression("[name] != null").evaluate(feat), True) - eq_(mapnik.Expression("[name] != true").evaluate(feat), True) - eq_(mapnik.Expression("[name] != false").evaluate(feat), True) + assert meta['srid'] == -1 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Point + + assert feat['gid'] == 1 + assert feat['name'] == 'name' + assert mapnik.Expression("[name] = 'name'").evaluate(feat) + assert not mapnik.Expression("[name] = ''").evaluate(feat) + assert not mapnik.Expression("[name] = null").evaluate(feat) + assert not mapnik.Expression("[name] = true").evaluate(feat) + assert not mapnik.Expression("[name] = false").evaluate(feat) + assert not mapnik.Expression("[name] != 'name'").evaluate(feat) + assert mapnik.Expression("[name] != ''").evaluate(feat) + assert mapnik.Expression("[name] != null").evaluate(feat) + assert mapnik.Expression("[name] != true").evaluate(feat) + assert mapnik.Expression("[name] != false").evaluate(feat) feat = fs.next() - eq_(feat['gid'], 2) - eq_(feat['name'], '') - eq_(mapnik.Expression("[name] = 'name'").evaluate(feat), False) - eq_(mapnik.Expression("[name] = ''").evaluate(feat), True) - eq_(mapnik.Expression("[name] = null").evaluate(feat), False) - eq_(mapnik.Expression("[name] = true").evaluate(feat), False) - eq_(mapnik.Expression("[name] = false").evaluate(feat), False) - eq_(mapnik.Expression("[name] != 'name'").evaluate(feat), True) - eq_(mapnik.Expression("[name] != ''").evaluate(feat), False) - eq_(mapnik.Expression("[name] != null").evaluate(feat), True) - eq_(mapnik.Expression("[name] != true").evaluate(feat), True) - eq_(mapnik.Expression("[name] != false").evaluate(feat), True) + assert feat['gid'] == 2 + assert feat['name'] == '' + assert mapnik.Expression("[name] = 'name'").evaluate(feat) == False + assert mapnik.Expression("[name] = ''").evaluate(feat) == True + assert mapnik.Expression("[name] = null").evaluate(feat) == False + assert mapnik.Expression("[name] = true").evaluate(feat) == False + assert mapnik.Expression("[name] = false").evaluate(feat) == False + assert mapnik.Expression("[name] != 'name'").evaluate(feat) == True + assert mapnik.Expression("[name] != ''").evaluate(feat) == False + assert mapnik.Expression("[name] != null").evaluate(feat) == True + assert mapnik.Expression("[name] != true").evaluate(feat) == True + assert mapnik.Expression("[name] != false").evaluate(feat) == True feat = fs.next() - eq_(feat['gid'], 3) - eq_(feat['name'], None) # null - eq_(mapnik.Expression("[name] = 'name'").evaluate(feat), False) - eq_(mapnik.Expression("[name] = ''").evaluate(feat), False) - eq_(mapnik.Expression("[name] = null").evaluate(feat), True) - eq_(mapnik.Expression("[name] = true").evaluate(feat), False) - eq_(mapnik.Expression("[name] = false").evaluate(feat), False) - eq_(mapnik.Expression("[name] != 'name'").evaluate(feat), True) + assert feat['gid'] == 3 + assert feat['name'] == None # null + assert mapnik.Expression("[name] = 'name'").evaluate(feat) == False + assert mapnik.Expression("[name] = ''").evaluate(feat) == False + assert mapnik.Expression("[name] = null").evaluate(feat) == True + assert mapnik.Expression("[name] = true").evaluate(feat) == False + assert mapnik.Expression("[name] = false").evaluate(feat) == False + assert mapnik.Expression("[name] != 'name'").evaluate(feat) == True # https://github.com/mapnik/mapnik/issues/1859 - eq_(mapnik.Expression("[name] != ''").evaluate(feat), False) - eq_(mapnik.Expression("[name] != null").evaluate(feat), False) - eq_(mapnik.Expression("[name] != true").evaluate(feat), True) - eq_(mapnik.Expression("[name] != false").evaluate(feat), True) + assert mapnik.Expression("[name] != ''").evaluate(feat) == False + assert mapnik.Expression("[name] != null").evaluate(feat) == False + assert mapnik.Expression("[name] != true").evaluate(feat) == True + assert mapnik.Expression("[name] != false").evaluate(feat) == True def test_null_comparision2(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='test10', @@ -866,64 +855,58 @@ def test_null_comparision2(): feat = fs.next() meta = ds.describe() - eq_(meta['srid'], -1) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) - - eq_(feat['gid'], 1) - eq_(feat['bool_field'], True) - eq_(mapnik.Expression("[bool_field] = 'name'").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = ''").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = null").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = true").evaluate(feat), True) - eq_(mapnik.Expression("[bool_field] = false").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] != 'name'").evaluate(feat), True) - eq_(mapnik.Expression("[bool_field] != ''").evaluate( - feat), True) # in 2.1.x used to be False - eq_(mapnik.Expression("[bool_field] != null").evaluate( - feat), True) # in 2.1.x used to be False - eq_(mapnik.Expression("[bool_field] != true").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] != false").evaluate(feat), True) + assert meta['srid'] == -1 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Point + + assert feat['gid'] == 1 + assert feat['bool_field'] + assert not mapnik.Expression("[bool_field] = 'name'").evaluate(feat) + assert not mapnik.Expression("[bool_field] = ''").evaluate(feat) + assert not mapnik.Expression("[bool_field] = null").evaluate(feat) + assert mapnik.Expression("[bool_field] = true").evaluate(feat) + assert not mapnik.Expression("[bool_field] = false").evaluate(feat) + assert mapnik.Expression("[bool_field] != 'name'").evaluate(feat) + assert mapnik.Expression("[bool_field] != ''").evaluate(feat) # in 2.1.x used to be False + assert mapnik.Expression("[bool_field] != null").evaluate(feat) # in 2.1.x used to be False + assert not mapnik.Expression("[bool_field] != true").evaluate(feat) + assert mapnik.Expression("[bool_field] != false").evaluate(feat) feat = fs.next() - eq_(feat['gid'], 2) - eq_(feat['bool_field'], False) - eq_(mapnik.Expression("[bool_field] = 'name'").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = ''").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = null").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = true").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = false").evaluate(feat), True) - eq_(mapnik.Expression("[bool_field] != 'name'").evaluate(feat), True) - eq_(mapnik.Expression("[bool_field] != ''").evaluate(feat), True) - eq_(mapnik.Expression("[bool_field] != null").evaluate( - feat), True) # in 2.1.x used to be False - eq_(mapnik.Expression("[bool_field] != true").evaluate(feat), True) - eq_(mapnik.Expression("[bool_field] != false").evaluate(feat), False) + assert feat['gid'] == 2 + assert not feat['bool_field'] + assert not mapnik.Expression("[bool_field] = 'name'").evaluate(feat) + assert not mapnik.Expression("[bool_field] = ''").evaluate(feat) + assert not mapnik.Expression("[bool_field] = null").evaluate(feat) + assert not mapnik.Expression("[bool_field] = true").evaluate(feat) + assert mapnik.Expression("[bool_field] = false").evaluate(feat) + assert mapnik.Expression("[bool_field] != 'name'").evaluate(feat) + assert mapnik.Expression("[bool_field] != ''").evaluate(feat) + assert mapnik.Expression("[bool_field] != null").evaluate(feat) # in 2.1.x used to be False + assert mapnik.Expression("[bool_field] != true").evaluate(feat) + assert not mapnik.Expression("[bool_field] != false").evaluate(feat) feat = fs.next() - eq_(feat['gid'], 3) - eq_(feat['bool_field'], None) # null - eq_(mapnik.Expression("[bool_field] = 'name'").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = ''").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = null").evaluate(feat), True) - eq_(mapnik.Expression("[bool_field] = true").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] = false").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] != 'name'").evaluate( - feat), True) # in 2.1.x used to be False + assert feat['gid'] == 3 + assert feat['bool_field'] == None # null + assert not mapnik.Expression("[bool_field] = 'name'").evaluate(feat) + assert not mapnik.Expression("[bool_field] = ''").evaluate(feat) + assert mapnik.Expression("[bool_field] = null").evaluate(feat) + assert not mapnik.Expression("[bool_field] = true").evaluate(feat) + assert not mapnik.Expression("[bool_field] = false").evaluate(feat) + assert mapnik.Expression("[bool_field] != 'name'").evaluate(feat) # in 2.1.x used to be False # https://github.com/mapnik/mapnik/issues/1859 - eq_(mapnik.Expression("[bool_field] != ''").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] != null").evaluate(feat), False) - eq_(mapnik.Expression("[bool_field] != true").evaluate( - feat), True) # in 2.1.x used to be False - eq_(mapnik.Expression("[bool_field] != false").evaluate( - feat), True) # in 2.1.x used to be False + assert not mapnik.Expression("[bool_field] != ''").evaluate(feat) + assert not mapnik.Expression("[bool_field] != null").evaluate(feat) + assert mapnik.Expression("[bool_field] != true").evaluate(feat) # in 2.1.x used to be False + assert mapnik.Expression("[bool_field] != false").evaluate(feat) # in 2.1.x used to be False # https://github.com/mapnik/mapnik/issues/1816 def test_exception_message_reporting(): try: mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='doesnotexist') except Exception as e: - eq_(str(e) != 'unidentifiable C++ exception', True) + assert str(e) != 'unidentifiable C++ exception' def test_null_id_field(): opts = {'type': 'postgis', @@ -933,15 +916,15 @@ def test_null_id_field(): ds = mapnik.Datasource(**opts) fs = ds.featureset() feat = fs.next() - eq_(feat.id(), long(1)) - eq_(feat['osm_id'], None) + assert feat.id() == int(1) + assert feat['osm_id'] == None meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None + assert meta['geometry_type'] == mapnik.DataGeometryType.Point + - @raises(StopIteration) def test_null_key_field(): opts = {'type': 'postgis', "key_field": 'osm_id', @@ -950,9 +933,10 @@ def test_null_key_field(): 'table': "(select null::bigint as osm_id, GeomFromEWKT('SRID=4326;POINT(0 0)') as geom) as tmp"} ds = mapnik.Datasource(**opts) fs = ds.featureset() - # should throw since key_field is null: StopIteration: No more - # features. - fs.next() + with pytest.raises(StopIteration): + # should throw since key_field is null: StopIteration: No more + # features. + fs.next() def test_psql_error_should_not_break_connection_pool(): # Bad request, will trigger an error when returning result @@ -969,15 +953,15 @@ def test_psql_error_should_not_break_connection_pool(): fs = ds_bad.featureset() count = sum(1 for f in fs) except RuntimeError as e: - assert 'invalid input syntax for integer' in str(e) + assert 'invalid input syntax for type integer' in str(e) failed = True - eq_(failed, True) + assert failed == True # Should be ok fs = ds_good.featureset() count = sum(1 for f in fs) - eq_(count, 8) + assert count == 8 def test_psql_error_should_give_back_connections_opened_for_lower_layers_to_the_pool(): map1 = mapnik.Map(600, 300) @@ -991,7 +975,7 @@ def test_psql_error_should_give_back_connections_opened_for_lower_layers_to_the_ buggy_s = mapnik.Style() buggy_r = mapnik.Rule() buggy_r.symbols.append(mapnik.PolygonSymbolizer()) - buggy_r.filter = mapnik.Filter("[fips] = 'FR'") + buggy_r.filter = mapnik.Expression("[fips] = 'FR'") buggy_s.rules.append(buggy_r) map1.append_style('style for buggy layer', buggy_s) buggy_layer = mapnik.Layer('this layer is buggy at runtime') @@ -1031,9 +1015,9 @@ def test_psql_error_should_give_back_connections_opened_for_lower_layers_to_the_ mapnik.render_to_file( map1, '/tmp/mapnik-postgis-test-map1.png', 'png') # Test must fail if error was not raised just above - eq_(False, True) + assert False == True except RuntimeError as e: - assert 'invalid input syntax for integer' in str(e) + assert 'invalid input syntax for type integer' in str(e) pass # This used to raise an exception before correction of issue 2042 mapnik.render_to_file(map2, '/tmp/mapnik-postgis-test-map2.png', 'png') @@ -1042,200 +1026,196 @@ def test_handling_of_zm_dimensions(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table='(select gid,ST_CoordDim(geom) as dim,name,geom from test12) as tmp', geometry_field='geom') - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['gid', 'dim', 'name']) - eq_(ds.field_types(), ['int', 'int', 'str']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['gid', 'dim' == 'name'] + assert ds.field_types(), ['int', 'int' == 'str'] fs = ds.featureset() meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), None) + assert meta['srid'] == 4326 + assert meta.get('key_field') == None # Note: this is incorrect because we only check first couple geoms - eq_(meta['geometry_type'], mapnik.DataGeometryType.Point) + assert meta['geometry_type'] == mapnik.DataGeometryType.Point # Point (2d) feat = fs.next() - eq_(feat.id(), 1) - eq_(feat['gid'], 1) - eq_(feat['dim'], 2) - eq_(feat['name'], 'Point') - eq_(feat.geometry.to_wkt(), 'POINT(0 0)') + assert feat.id() == 1 + assert feat['gid'] == 1 + assert feat['dim'] == 2 + assert feat['name'] == 'Point' + assert feat.geometry.to_wkt() == 'POINT(0 0)' # PointZ feat = fs.next() - eq_(feat.id(), 2) - eq_(feat['gid'], 2) - eq_(feat['dim'], 3) - eq_(feat['name'], 'PointZ') - eq_(feat.geometry.to_wkt(), 'POINT(0 0)') + assert feat.id() == 2 + assert feat['gid'] == 2 + assert feat['dim'] == 3 + assert feat['name'] == 'PointZ' + assert feat.geometry.to_wkt() == 'POINT(0 0)' # PointM feat = fs.next() - eq_(feat.id(), 3) - eq_(feat['gid'], 3) - eq_(feat['dim'], 3) - eq_(feat['name'], 'PointM') - eq_(feat.geometry.to_wkt(), 'POINT(0 0)') + assert feat.id() == 3 + assert feat['gid'] == 3 + assert feat['dim'] == 3 + assert feat['name'] == 'PointM' + assert feat.geometry.to_wkt() == 'POINT(0 0)' # PointZM feat = fs.next() - eq_(feat.id(), 4) - eq_(feat['gid'], 4) - eq_(feat['dim'], 4) - eq_(feat['name'], 'PointZM') + assert feat.id() == 4 + assert feat['gid'] == 4 + assert feat['dim'] == 4 + assert feat['name'] == 'PointZM' - eq_(feat.geometry.to_wkt(), 'POINT(0 0)') + assert feat.geometry.to_wkt() == 'POINT(0 0)' # MultiPoint feat = fs.next() - eq_(feat.id(), 5) - eq_(feat['gid'], 5) - eq_(feat['dim'], 2) - eq_(feat['name'], 'MultiPoint') - eq_(feat.geometry.to_wkt(), 'MULTIPOINT(0 0,1 1)') + assert feat.id() == 5 + assert feat['gid'] == 5 + assert feat['dim'] == 2 + assert feat['name'] == 'MultiPoint' + assert feat.geometry.to_wkt() == 'MULTIPOINT(0 0,1 1)' # MultiPointZ feat = fs.next() - eq_(feat.id(), 6) - eq_(feat['gid'], 6) - eq_(feat['dim'], 3) - eq_(feat['name'], 'MultiPointZ') - eq_(feat.geometry.to_wkt(), 'MULTIPOINT(0 0,1 1)') + assert feat.id() == 6 + assert feat['gid'] == 6 + assert feat['dim'] == 3 + assert feat['name'] == 'MultiPointZ' + assert feat.geometry.to_wkt() == 'MULTIPOINT(0 0,1 1)' # MultiPointM feat = fs.next() - eq_(feat.id(), 7) - eq_(feat['gid'], 7) - eq_(feat['dim'], 3) - eq_(feat['name'], 'MultiPointM') - eq_(feat.geometry.to_wkt(), 'MULTIPOINT(0 0,1 1)') + assert feat.id() == 7 + assert feat['gid'] == 7 + assert feat['dim'] == 3 + assert feat['name'] == 'MultiPointM' + assert feat.geometry.to_wkt() == 'MULTIPOINT(0 0,1 1)' # MultiPointZM feat = fs.next() - eq_(feat.id(), 8) - eq_(feat['gid'], 8) - eq_(feat['dim'], 4) - eq_(feat['name'], 'MultiPointZM') - eq_(feat.geometry.to_wkt(), 'MULTIPOINT(0 0,1 1)') + assert feat.id() == 8 + assert feat['gid'] == 8 + assert feat['dim'] == 4 + assert feat['name'] == 'MultiPointZM' + assert feat.geometry.to_wkt() == 'MULTIPOINT(0 0,1 1)' # LineString feat = fs.next() - eq_(feat.id(), 9) - eq_(feat['gid'], 9) - eq_(feat['dim'], 2) - eq_(feat['name'], 'LineString') - eq_(feat.geometry.to_wkt(), 'LINESTRING(0 0,1 1)') + assert feat.id() == 9 + assert feat['gid'] == 9 + assert feat['dim'] == 2 + assert feat['name'] == 'LineString' + assert feat.geometry.to_wkt() == 'LINESTRING(0 0,1 1)' # LineStringZ feat = fs.next() - eq_(feat.id(), 10) - eq_(feat['gid'], 10) - eq_(feat['dim'], 3) - eq_(feat['name'], 'LineStringZ') - eq_(feat.geometry.to_wkt(), 'LINESTRING(0 0,1 1)') + assert feat.id() == 10 + assert feat['gid'] == 10 + assert feat['dim'] == 3 + assert feat['name'] == 'LineStringZ' + assert feat.geometry.to_wkt() == 'LINESTRING(0 0,1 1)' # LineStringM feat = fs.next() - eq_(feat.id(), 11) - eq_(feat['gid'], 11) - eq_(feat['dim'], 3) - eq_(feat['name'], 'LineStringM') - eq_(feat.geometry.to_wkt(), 'LINESTRING(0 0,1 1)') + assert feat.id() == 11 + assert feat['gid'] == 11 + assert feat['dim'] == 3 + assert feat['name'] == 'LineStringM' + assert feat.geometry.to_wkt() == 'LINESTRING(0 0,1 1)' # LineStringZM feat = fs.next() - eq_(feat.id(), 12) - eq_(feat['gid'], 12) - eq_(feat['dim'], 4) - eq_(feat['name'], 'LineStringZM') - eq_(feat.geometry.to_wkt(), 'LINESTRING(0 0,1 1)') + assert feat.id() == 12 + assert feat['gid'] == 12 + assert feat['dim'] == 4 + assert feat['name'] == 'LineStringZM' + assert feat.geometry.to_wkt() == 'LINESTRING(0 0,1 1)' # Polygon feat = fs.next() - eq_(feat.id(), 13) - eq_(feat['gid'], 13) - eq_(feat['name'], 'Polygon') - eq_(feat.geometry.to_wkt(), 'POLYGON((0 0,1 1,2 2,0 0))') + assert feat.id() == 13 + assert feat['gid'] == 13 + assert feat['name'] == 'Polygon' + assert feat.geometry.to_wkt() == 'POLYGON((0 0,1 1,2 2,0 0))' # PolygonZ feat = fs.next() - eq_(feat.id(), 14) - eq_(feat['gid'], 14) - eq_(feat['name'], 'PolygonZ') - eq_(feat.geometry.to_wkt(), 'POLYGON((0 0,1 1,2 2,0 0))') + assert feat.id() == 14 + assert feat['gid'] == 14 + assert feat['name'] == 'PolygonZ' + assert feat.geometry.to_wkt() == 'POLYGON((0 0,1 1,2 2,0 0))' # PolygonM feat = fs.next() - eq_(feat.id(), 15) - eq_(feat['gid'], 15) - eq_(feat['name'], 'PolygonM') - eq_(feat.geometry.to_wkt(), 'POLYGON((0 0,1 1,2 2,0 0))') + assert feat.id() == 15 + assert feat['gid'] == 15 + assert feat['name'] == 'PolygonM' + assert feat.geometry.to_wkt() == 'POLYGON((0 0,1 1,2 2,0 0))' # PolygonZM feat = fs.next() - eq_(feat.id(), 16) - eq_(feat['gid'], 16) - eq_(feat['name'], 'PolygonZM') - eq_(feat.geometry.to_wkt(), 'POLYGON((0 0,1 1,2 2,0 0))') + assert feat.id() == 16 + assert feat['gid'] == 16 + assert feat['name'] == 'PolygonZM' + assert feat.geometry.to_wkt() == 'POLYGON((0 0,1 1,2 2,0 0))' # MultiLineString feat = fs.next() - eq_(feat.id(), 17) - eq_(feat['gid'], 17) - eq_(feat['name'], 'MultiLineString') - eq_(feat.geometry.to_wkt(), 'MULTILINESTRING((0 0,1 1),(2 2,3 3))') + assert feat.id() == 17 + assert feat['gid'] == 17 + assert feat['name'] == 'MultiLineString' + assert feat.geometry.to_wkt() == 'MULTILINESTRING((0 0,1 1),(2 2,3 3))' # MultiLineStringZ feat = fs.next() - eq_(feat.id(), 18) - eq_(feat['gid'], 18) - eq_(feat['name'], 'MultiLineStringZ') - eq_(feat.geometry.to_wkt(), 'MULTILINESTRING((0 0,1 1),(2 2,3 3))') + assert feat.id() == 18 + assert feat['gid'] == 18 + assert feat['name'] == 'MultiLineStringZ' + assert feat.geometry.to_wkt() == 'MULTILINESTRING((0 0,1 1),(2 2,3 3))' # MultiLineStringM feat = fs.next() - eq_(feat.id(), 19) - eq_(feat['gid'], 19) - eq_(feat['name'], 'MultiLineStringM') - eq_(feat.geometry.to_wkt(), 'MULTILINESTRING((0 0,1 1),(2 2,3 3))') + assert feat.id() == 19 + assert feat['gid'] == 19 + assert feat['name'] == 'MultiLineStringM' + assert feat.geometry.to_wkt() == 'MULTILINESTRING((0 0,1 1),(2 2,3 3))' # MultiLineStringZM feat = fs.next() - eq_(feat.id(), 20) - eq_(feat['gid'], 20) - eq_(feat['name'], 'MultiLineStringZM') - eq_(feat.geometry.to_wkt(), 'MULTILINESTRING((0 0,1 1),(2 2,3 3))') + assert feat.id() == 20 + assert feat['gid'] == 20 + assert feat['name'] == 'MultiLineStringZM' + assert feat.geometry.to_wkt() == 'MULTILINESTRING((0 0,1 1),(2 2,3 3))' # MultiPolygon feat = fs.next() - eq_(feat.id(), 21) - eq_(feat['gid'], 21) - eq_(feat['name'], 'MultiPolygon') - eq_(feat.geometry.to_wkt(), - 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))') + assert feat.id() == 21 + assert feat['gid'] == 21 + assert feat['name'] == 'MultiPolygon' + assert feat.geometry.to_wkt() == 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))' # MultiPolygonZ feat = fs.next() - eq_(feat.id(), 22) - eq_(feat['gid'], 22) - eq_(feat['name'], 'MultiPolygonZ') - eq_(feat.geometry.to_wkt(), - 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))') + assert feat.id() == 22 + assert feat['gid'] == 22 + assert feat['name'] == 'MultiPolygonZ' + assert feat.geometry.to_wkt() == 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))' # MultiPolygonM feat = fs.next() - eq_(feat.id(), 23) - eq_(feat['gid'], 23) - eq_(feat['name'], 'MultiPolygonM') - eq_(feat.geometry.to_wkt(), - 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))') + assert feat.id() == 23 + assert feat['gid'] == 23 + assert feat['name'] == 'MultiPolygonM' + assert feat.geometry.to_wkt() == 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))' # MultiPolygonZM feat = fs.next() - eq_(feat.id(), 24) - eq_(feat['gid'], 24) - eq_(feat['name'], 'MultiPolygonZM') - eq_(feat.geometry.to_wkt(), - 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))') + assert feat.id() == 24 + assert feat['gid'] == 24 + assert feat['name'] == 'MultiPolygonZM' + assert feat.geometry.to_wkt() == 'MULTIPOLYGON(((0 0,1 1,2 2,0 0)),((0 0,1 1,2 2,0 0)))' def test_handling_of_discarded_key_field(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, @@ -1244,7 +1224,7 @@ def test_handling_of_discarded_key_field(): key_field_as_attribute=False) fs = ds.featureset() feat = fs.next() - eq_(feat['name'],'Point') + assert feat['name'] == 'Point' def test_variable_in_subquery1(): ds = mapnik.PostGIS(dbname=MAPNIK_TEST_DBNAME, table=''' @@ -1253,12 +1233,12 @@ def test_variable_in_subquery1(): autodetect_key_field=True) fs = ds.featureset(variables={'zoom': 30}) for id in range(1, 5): - eq_(fs.next().id(), id) + assert fs.next().id() == id meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta.get('key_field'), "gid") - eq_(meta['geometry_type'], None) + assert meta['srid'] == 4326 + assert meta.get('key_field') == "gid" + assert meta['geometry_type'] == None # currently needs manual `geometry_table` passed # to avoid misparse of `geometry_table` @@ -1272,11 +1252,11 @@ def test_broken_parsing_of_comments(): geometry_table='test') fs = ds.featureset() for id in range(1, 5): - eq_(fs.next().id(), id) + assert fs.next().id() == id meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Collection) + assert meta['srid'] == 4326 + assert meta['geometry_type'] == mapnik.DataGeometryType.Collection # same # to avoid misparse of `geometry_table` @@ -1290,14 +1270,10 @@ def test_broken_parsing_of_comments(): geometry_table='test') fs = ds.featureset() for id in range(1, 5): - eq_(fs.next().id(), id) + assert fs.next().id() == id meta = ds.describe() - eq_(meta['srid'], 4326) - eq_(meta['geometry_type'], mapnik.DataGeometryType.Collection) + assert meta['srid'] == 4326 + assert meta['geometry_type'] == mapnik.DataGeometryType.Collection atexit.register(postgis_takedown) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) From 45ed937c3ab24fc42f9a10c46882dc730be95861 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 9 Feb 2023 11:38:35 +0000 Subject: [PATCH 16/37] Unit tests [WIP] --- test/python_tests/postgis_test.py | 3 +- test/python_tests/sqlite_test.py | 928 ++++++++++++------------ test/python_tests/style_test.py | 23 +- test/python_tests/webp_encoding_test.py | 43 +- 4 files changed, 472 insertions(+), 525 deletions(-) diff --git a/test/python_tests/postgis_test.py b/test/python_tests/postgis_test.py index 0549c94c1..969084d99 100644 --- a/test/python_tests/postgis_test.py +++ b/test/python_tests/postgis_test.py @@ -5,10 +5,11 @@ from subprocess import PIPE, Popen import mapnik import pytest +from .utilities import execution_path MAPNIK_TEST_DBNAME = 'mapnik-tmp-postgis-test-db' POSTGIS_TEMPLATE_DBNAME = 'template_postgis' -SHAPEFILE = './test/data/shp/world_merc.shp' +SHAPEFILE = os.path.join(execution_path('.'), '../data/shp/world_merc.shp') def call(cmd, silent=False): stdin, stderr = Popen(cmd, shell=True, stdout=PIPE, diff --git a/test/python_tests/sqlite_test.py b/test/python_tests/sqlite_test.py index 9720e3bf0..5e4345db8 100644 --- a/test/python_tests/sqlite_test.py +++ b/test/python_tests/sqlite_test.py @@ -1,28 +1,21 @@ -#!/usr/bin/env python - import os - -from nose.tools import eq_, raises - import mapnik +import pytest +from .utilities import execution_path -from .utilities import execution_path, run_all - - -def setup(): +@pytest.fixture(scope="module") +def setup_and_teardown(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) - - -def teardown(): + yield index = '../data/sqlite/world.sqlite.index' if os.path.exists(index): os.unlink(index) if 'sqlite' in mapnik.DatasourceCache.plugin_names(): - def test_attachdb_with_relative_file(): + def test_attachdb_with_relative_file(setup_and_teardown): # The point table and index is in the qgis_spatiallite.sqlite # database. If either is not found, then this fails ds = mapnik.SQLite(file='../data/sqlite/world.sqlite', @@ -31,7 +24,7 @@ def test_attachdb_with_relative_file(): ) fs = ds.featureset() feature = fs.next() - eq_(feature['pkuid'], 1) + assert feature['pkuid'] == 1 test_attachdb_with_relative_file.requires_data = True @@ -52,7 +45,7 @@ def test_attachdb_with_multiple_files(): except StopIteration: pass # the above should not throw but will result in no features - eq_(feature, None) + assert feature == None test_attachdb_with_multiple_files.requires_data = True @@ -65,7 +58,7 @@ def test_attachdb_with_absolute_file(): ) fs = ds.featureset() feature = fs.next() - eq_(feature['pkuid'], 1) + assert feature['pkuid'] == 1 test_attachdb_with_absolute_file.requires_data = True @@ -86,7 +79,7 @@ def test_attachdb_with_index(): feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None test_attachdb_with_index.requires_data = True @@ -107,7 +100,7 @@ def test_attachdb_with_explicit_index(): feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None test_attachdb_with_explicit_index.requires_data = True @@ -116,70 +109,68 @@ def test_attachdb_with_sql_join(): table='(select * from world_merc INNER JOIN business on world_merc.iso3 = business.ISO3 limit 100)', attachdb='busines@business.sqlite' ) - eq_(len(ds.fields()), 29) - eq_(ds.fields(), - ['OGC_FID', - 'fips', - 'iso2', - 'iso3', - 'un', - 'name', - 'area', - 'pop2005', - 'region', - 'subregion', - 'lon', - 'lat', - 'ISO3:1', - '1995', - '1996', - '1997', - '1998', - '1999', - '2000', - '2001', - '2002', - '2003', - '2004', - '2005', - '2006', - '2007', - '2008', - '2009', - '2010']) - eq_(ds.field_types(), - ['int', - 'str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float', - 'str', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int']) + assert len(ds.fields()) == 29 + assert ds.fields() == ['OGC_FID', + 'fips', + 'iso2', + 'iso3', + 'un', + 'name', + 'area', + 'pop2005', + 'region', + 'subregion', + 'lon', + 'lat', + 'ISO3:1', + '1995', + '1996', + '1997', + '1998', + '1999', + '2000', + '2001', + '2002', + '2003', + '2004', + '2005', + '2006', + '2007', + '2008', + '2009', + '2010'] + assert ds.field_types() == ['int', + 'str', + 'str', + 'str', + 'int', + 'str', + 'int', + 'int', + 'int', + 'int', + 'float', + 'float', + 'str', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int'] fs = ds.featureset() feature = fs.next() - eq_(feature.id(), 1) + assert feature.id() == 1 expected = { 1995: 0, 1996: 0, @@ -215,7 +206,7 @@ def test_attachdb_with_sql_join(): } for k, v in expected.items(): try: - eq_(feature[str(k)], v) + assert feature[str(k)] == v except: #import pdb;pdb.set_trace() print('invalid key/v %s/%s for: %s' % (k, v, feature)) @@ -227,68 +218,66 @@ def test_attachdb_with_sql_join_count(): table='(select * from world_merc INNER JOIN business on world_merc.iso3 = business.ISO3 limit 100)', attachdb='busines@business.sqlite' ) - eq_(len(ds.fields()), 29) - eq_(ds.fields(), - ['OGC_FID', - 'fips', - 'iso2', - 'iso3', - 'un', - 'name', - 'area', - 'pop2005', - 'region', - 'subregion', - 'lon', - 'lat', - 'ISO3:1', - '1995', - '1996', - '1997', - '1998', - '1999', - '2000', - '2001', - '2002', - '2003', - '2004', - '2005', - '2006', - '2007', - '2008', - '2009', - '2010']) - eq_(ds.field_types(), - ['int', - 'str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float', - 'str', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int']) - eq_(len(list(ds.all_features())), 100) + assert len(ds.fields()) == 29 + assert ds.fields() == ['OGC_FID', + 'fips', + 'iso2', + 'iso3', + 'un', + 'name', + 'area', + 'pop2005', + 'region', + 'subregion', + 'lon', + 'lat', + 'ISO3:1', + '1995', + '1996', + '1997', + '1998', + '1999', + '2000', + '2001', + '2002', + '2003', + '2004', + '2005', + '2006', + '2007', + '2008', + '2009', + '2010'] + assert ds.field_types() == ['int', + 'str', + 'str', + 'str', + 'int', + 'str', + 'int', + 'int', + 'int', + 'int', + 'float', + 'float', + 'str', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int'] + assert len(list(ds.all_features())) == 100 test_attachdb_with_sql_join_count.requires_data = True @@ -302,68 +291,66 @@ def test_attachdb_with_sql_join_count2(): table='(select * from world_merc INNER JOIN business on world_merc.iso3 = business.ISO3)', attachdb='busines@business.sqlite' ) - eq_(len(ds.fields()), 29) - eq_(ds.fields(), - ['OGC_FID', - 'fips', - 'iso2', - 'iso3', - 'un', - 'name', - 'area', - 'pop2005', - 'region', - 'subregion', - 'lon', - 'lat', - 'ISO3:1', - '1995', - '1996', - '1997', - '1998', - '1999', - '2000', - '2001', - '2002', - '2003', - '2004', - '2005', - '2006', - '2007', - '2008', - '2009', - '2010']) - eq_(ds.field_types(), - ['int', - 'str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float', - 'str', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int']) - eq_(len(list(ds.all_features())), 192) + assert len(ds.fields()) == 29 + assert ds.fields() == ['OGC_FID', + 'fips', + 'iso2', + 'iso3', + 'un', + 'name', + 'area', + 'pop2005', + 'region', + 'subregion', + 'lon', + 'lat', + 'ISO3:1', + '1995', + '1996', + '1997', + '1998', + '1999', + '2000', + '2001', + '2002', + '2003', + '2004', + '2005', + '2006', + '2007', + '2008', + '2009', + '2010'] + assert ds.field_types() == ['int', + 'str', + 'str', + 'str', + 'int', + 'str', + 'int', + 'int', + 'int', + 'int', + 'float', + 'float', + 'str', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int'] + assert len(list(ds.all_features())) == 192 test_attachdb_with_sql_join_count2.requires_data = True @@ -375,68 +362,66 @@ def test_attachdb_with_sql_join_count3(): table='(select * from (select * from world_merc where !intersects!) as world_merc INNER JOIN business on world_merc.iso3 = business.ISO3)', attachdb='busines@business.sqlite' ) - eq_(len(ds.fields()), 29) - eq_(ds.fields(), - ['OGC_FID', - 'fips', - 'iso2', - 'iso3', - 'un', - 'name', - 'area', - 'pop2005', - 'region', - 'subregion', - 'lon', - 'lat', - 'ISO3:1', - '1995', - '1996', - '1997', - '1998', - '1999', - '2000', - '2001', - '2002', - '2003', - '2004', - '2005', - '2006', - '2007', - '2008', - '2009', - '2010']) - eq_(ds.field_types(), - ['int', - 'str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float', - 'str', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int']) - eq_(len(list(ds.all_features())), 192) + assert len(ds.fields()) == 29 + assert ds.fields() == ['OGC_FID', + 'fips', + 'iso2', + 'iso3', + 'un', + 'name', + 'area', + 'pop2005', + 'region', + 'subregion', + 'lon', + 'lat', + 'ISO3:1', + '1995', + '1996', + '1997', + '1998', + '1999', + '2000', + '2001', + '2002', + '2003', + '2004', + '2005', + '2006', + '2007', + '2008', + '2009', + '2010'] + assert ds.field_types() == ['int', + 'str', + 'str', + 'str', + 'int', + 'str', + 'int', + 'int', + 'int', + 'int', + 'float', + 'float', + 'str', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int'] + assert len(list(ds.all_features())) == 192 test_attachdb_with_sql_join_count3.requires_data = True @@ -448,68 +433,66 @@ def test_attachdb_with_sql_join_count4(): table='(select * from (select * from world_merc where !intersects! limit 1) as world_merc INNER JOIN business on world_merc.iso3 = business.ISO3)', attachdb='busines@business.sqlite' ) - eq_(len(ds.fields()), 29) - eq_(ds.fields(), - ['OGC_FID', - 'fips', - 'iso2', - 'iso3', - 'un', - 'name', - 'area', - 'pop2005', - 'region', - 'subregion', - 'lon', - 'lat', - 'ISO3:1', - '1995', - '1996', - '1997', - '1998', - '1999', - '2000', - '2001', - '2002', - '2003', - '2004', - '2005', - '2006', - '2007', - '2008', - '2009', - '2010']) - eq_(ds.field_types(), - ['int', - 'str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float', - 'str', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int', - 'int']) - eq_(len(list(ds.all_features())), 1) + assert len(ds.fields()) == 29 + assert ds.fields() == ['OGC_FID', + 'fips', + 'iso2', + 'iso3', + 'un', + 'name', + 'area', + 'pop2005', + 'region', + 'subregion', + 'lon', + 'lat', + 'ISO3:1', + '1995', + '1996', + '1997', + '1998', + '1999', + '2000', + '2001', + '2002', + '2003', + '2004', + '2005', + '2006', + '2007', + '2008', + '2009', + '2010'] + assert ds.field_types() == ['int', + 'str', + 'str', + 'str', + 'int', + 'str', + 'int', + 'int', + 'int', + 'int', + 'float', + 'float', + 'str', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int', + 'int'] + assert len(list(ds.all_features())) == 1 test_attachdb_with_sql_join_count4.requires_data = True @@ -523,34 +506,32 @@ def test_attachdb_with_sql_join_count5(): ) # nothing is able to join to business so we don't pick up business # schema - eq_(len(ds.fields()), 12) - eq_(ds.fields(), - ['OGC_FID', - 'fips', - 'iso2', - 'iso3', - 'un', - 'name', - 'area', - 'pop2005', - 'region', - 'subregion', - 'lon', - 'lat']) - eq_(ds.field_types(), - ['int', - 'str', - 'str', - 'str', - 'int', - 'str', - 'int', - 'int', - 'int', - 'int', - 'float', - 'float']) - eq_(len(list(ds.all_features())), 0) + assert len(ds.fields()) == 12 + assert ds.fields() == ['OGC_FID', + 'fips', + 'iso2', + 'iso3', + 'un', + 'name', + 'area', + 'pop2005', + 'region', + 'subregion', + 'lon', + 'lat'] + assert ds.field_types() == ['int', + 'str', + 'str', + 'str', + 'int', + 'str', + 'int', + 'int', + 'int', + 'int', + 'float', + 'float'] + assert len(list(ds.all_features())) == 0 test_attachdb_with_sql_join_count5.requires_data = True @@ -560,52 +541,52 @@ def test_subqueries(): ) fs = ds.featureset() feature = fs.next() - eq_(feature['OGC_FID'], 1) - eq_(feature['fips'], u'AC') - eq_(feature['iso2'], u'AG') - eq_(feature['iso3'], u'ATG') - eq_(feature['un'], 28) - eq_(feature['name'], u'Antigua and Barbuda') - eq_(feature['area'], 44) - eq_(feature['pop2005'], 83039) - eq_(feature['region'], 19) - eq_(feature['subregion'], 29) - eq_(feature['lon'], -61.783) - eq_(feature['lat'], 17.078) + assert feature['OGC_FID'] == 1 + assert feature['fips'] == u'AC' + assert feature['iso2'] == u'AG' + assert feature['iso3'] == u'ATG' + assert feature['un'] == 28 + assert feature['name'] == u'Antigua and Barbuda' + assert feature['area'] == 44 + assert feature['pop2005'] == 83039 + assert feature['region'] == 19 + assert feature['subregion'] == 29 + assert feature['lon'] == -61.783 + assert feature['lat'] == 17.078 ds = mapnik.SQLite(file='../data/sqlite/world.sqlite', table='(select * from world_merc)', ) fs = ds.featureset() feature = fs.next() - eq_(feature['OGC_FID'], 1) - eq_(feature['fips'], u'AC') - eq_(feature['iso2'], u'AG') - eq_(feature['iso3'], u'ATG') - eq_(feature['un'], 28) - eq_(feature['name'], u'Antigua and Barbuda') - eq_(feature['area'], 44) - eq_(feature['pop2005'], 83039) - eq_(feature['region'], 19) - eq_(feature['subregion'], 29) - eq_(feature['lon'], -61.783) - eq_(feature['lat'], 17.078) + assert feature['OGC_FID'] == 1 + assert feature['fips'] == u'AC' + assert feature['iso2'] == u'AG' + assert feature['iso3'] == u'ATG' + assert feature['un'] == 28 + assert feature['name'] == u'Antigua and Barbuda' + assert feature['area'] == 44 + assert feature['pop2005'] == 83039 + assert feature['region'] == 19 + assert feature['subregion'] == 29 + assert feature['lon'] == -61.783 + assert feature['lat'] == 17.078 ds = mapnik.SQLite(file='../data/sqlite/world.sqlite', table='(select OGC_FID,GEOMETRY from world_merc)', ) fs = ds.featureset() feature = fs.next() - eq_(feature['OGC_FID'], 1) - eq_(len(feature), 1) + assert feature['OGC_FID'] == 1 + assert len(feature) == 1 ds = mapnik.SQLite(file='../data/sqlite/world.sqlite', table='(select GEOMETRY,OGC_FID,fips from world_merc)', ) fs = ds.featureset() feature = fs.next() - eq_(feature['OGC_FID'], 1) - eq_(feature['fips'], u'AC') + assert feature['OGC_FID'] == 1 + assert feature['fips'] == u'AC' # same as above, except with alias like postgres requires # TODO - should we try to make this work? @@ -615,16 +596,16 @@ def test_subqueries(): # ) #fs = ds.featureset() #feature = fs.next() - # eq_(feature['aliased_id'],1) - # eq_(feature['fips'],u'AC') + # assert feature['aliased_id'] == 1 + # assert feature['fips'] == u'AC' ds = mapnik.SQLite(file='../data/sqlite/world.sqlite', table='(select GEOMETRY,OGC_FID,OGC_FID as rowid,fips from world_merc)', ) fs = ds.featureset() feature = fs.next() - eq_(feature['rowid'], 1) - eq_(feature['fips'], u'AC') + assert feature['rowid'] == 1 + assert feature['fips'] == u'AC' test_subqueries.requires_data = True @@ -638,74 +619,73 @@ def test_empty_db(): feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None test_empty_db.requires_data = True - @raises(RuntimeError) + def test_that_nonexistant_query_field_throws(**kwargs): ds = mapnik.SQLite(file='../data/sqlite/empty.db', table='empty', ) - eq_(len(ds.fields()), 25) - eq_(ds.fields(), - ['OGC_FID', - 'scalerank', - 'labelrank', - 'featurecla', - 'sovereignt', - 'sov_a3', - 'adm0_dif', - 'level', - 'type', - 'admin', - 'adm0_a3', - 'geou_dif', - 'name', - 'abbrev', - 'postal', - 'name_forma', - 'terr_', - 'name_sort', - 'map_color', - 'pop_est', - 'gdp_md_est', - 'fips_10_', - 'iso_a2', - 'iso_a3', - 'iso_n3']) - eq_(ds.field_types(), - ['int', - 'int', - 'int', - 'str', - 'str', - 'str', - 'float', - 'float', - 'str', - 'str', - 'str', - 'float', - 'str', - 'str', - 'str', - 'str', - 'str', - 'str', - 'float', - 'float', - 'float', - 'float', - 'str', - 'str', - 'float']) + assert len(ds.fields()) == 25 + assert ds.fields() == ['OGC_FID', + 'scalerank', + 'labelrank', + 'featurecla', + 'sovereignt', + 'sov_a3', + 'adm0_dif', + 'level', + 'type', + 'admin', + 'adm0_a3', + 'geou_dif', + 'name', + 'abbrev', + 'postal', + 'name_forma', + 'terr_', + 'name_sort', + 'map_color', + 'pop_est', + 'gdp_md_est', + 'fips_10_', + 'iso_a2', + 'iso_a3', + 'iso_n3'] + assert ds.field_types() == ['int', + 'int', + 'int', + 'str', + 'str', + 'str', + 'float', + 'float', + 'str', + 'str', + 'str', + 'float', + 'str', + 'str', + 'str', + 'str', + 'str', + 'str', + 'float', + 'float', + 'float', + 'float', + 'str', + 'str', + 'float'] query = mapnik.Query(ds.envelope()) for fld in ds.fields(): query.add_property_name(fld) # also add an invalid one, triggering throw query.add_property_name('bogus') - ds.features(query) + with pytest.raises(RuntimeError): + ds.features(query) test_that_nonexistant_query_field_throws.requires_data = True @@ -719,7 +699,7 @@ def test_intersects_token1(): feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None test_intersects_token1.requires_data = True @@ -733,7 +713,7 @@ def test_intersects_token2(): feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None test_intersects_token2.requires_data = True @@ -747,7 +727,7 @@ def test_intersects_token3(): feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None test_intersects_token3.requires_data = True @@ -766,15 +746,15 @@ def test_db_with_one_text_column(): use_spatial_index=False, key_field='alias' ) - eq_(len(ds.fields()), 1) - eq_(ds.fields(), ['alias']) - eq_(ds.field_types(), ['str']) + assert len(ds.fields()) == 1 + assert ds.fields() == ['alias'] + assert ds.field_types() == ['str'] fs = list(ds.all_features()) - eq_(len(fs), 1) + assert len(fs) == 1 feat = fs[0] - eq_(feat.id(), 0) # should be 1? - eq_(feat['alias'], 'test') - eq_(feat.geometry.to_wkt(), 'POINT(0 0)') + assert feat.id() == 0 # should be 1? + assert feat['alias'] == 'test' + assert feat.geometry.to_wkt() == 'POINT(0 0)' def test_db_with_one_untyped_column(): # form up an in-memory test db @@ -791,9 +771,9 @@ def test_db_with_one_untyped_column(): ) # ensure the untyped column is found - eq_(len(ds.fields()), 2) - eq_(ds.fields(), ['rowid', 'untyped']) - eq_(ds.field_types(), ['int', 'str']) + assert len(ds.fields()) == 2 + assert ds.fields(), ['rowid' == 'untyped'] + assert ds.field_types(), ['int' == 'str'] def test_db_with_one_untyped_column_using_subquery(): # form up an in-memory test db @@ -810,27 +790,27 @@ def test_db_with_one_untyped_column_using_subquery(): ) # ensure the untyped column is found - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['rowid', 'untyped', 'rowid']) - eq_(ds.field_types(), ['int', 'str', 'int']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['rowid', 'untyped' == 'rowid'] + assert ds.field_types(), ['int', 'str' == 'int'] def test_that_64bit_int_fields_work(): ds = mapnik.SQLite(file='../data/sqlite/64bit_int.sqlite', table='int_table', use_spatial_index=False ) - eq_(len(ds.fields()), 3) - eq_(ds.fields(), ['OGC_FID', 'id', 'bigint']) - eq_(ds.field_types(), ['int', 'int', 'int']) + assert len(ds.fields()) == 3 + assert ds.fields(), ['OGC_FID', 'id' == 'bigint'] + assert ds.field_types(), ['int', 'int' == 'int'] fs = ds.featureset() feat = fs.next() - eq_(feat.id(), 1) - eq_(feat['OGC_FID'], 1) - eq_(feat['bigint'], 2147483648) + assert feat.id() == 1 + assert feat['OGC_FID'] == 1 + assert feat['bigint'] == 2147483648 feat = fs.next() - eq_(feat.id(), 2) - eq_(feat['OGC_FID'], 2) - eq_(feat['bigint'], 922337203685477580) + assert feat.id() == 2 + assert feat['OGC_FID'] == 2 + assert feat['bigint'] == 922337203685477580 test_that_64bit_int_fields_work.requires_data = True @@ -860,11 +840,5 @@ def test_null_id_field(): feature = fs.next() except StopIteration: pass - eq_(feature, None) + assert feature == None mapnik.logger.set_severity(default_logging_severity) - -if __name__ == "__main__": - setup() - result = run_all(eval(x) for x in dir() if x.startswith("test_")) - teardown() - exit(result) diff --git a/test/python_tests/style_test.py b/test/python_tests/style_test.py index ff2c05e8f..00dca93da 100644 --- a/test/python_tests/style_test.py +++ b/test/python_tests/style_test.py @@ -1,21 +1,10 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -from nose.tools import eq_ - import mapnik -from .utilities import run_all - - def test_style_init(): s = mapnik.Style() - eq_(s.filter_mode, mapnik.filter_mode.ALL) - eq_(len(s.rules), 0) - eq_(s.opacity, 1) - eq_(s.comp_op, None) - eq_(s.image_filters, "") - eq_(s.image_filters_inflate, False) - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert s.filter_mode == mapnik.filter_mode.ALL + assert len(s.rules) == 0 + assert s.opacity == 1 + assert s.comp_op == None + assert s.image_filters == "" + assert not s.image_filters_inflate diff --git a/test/python_tests/webp_encoding_test.py b/test/python_tests/webp_encoding_test.py index ccd8f4229..76809af7e 100644 --- a/test/python_tests/webp_encoding_test.py +++ b/test/python_tests/webp_encoding_test.py @@ -1,20 +1,6 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- -from __future__ import absolute_import, print_function - -import os - -from nose.tools import eq_, raises - import mapnik - -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) +import os +import pytest if mapnik.has_webp(): tmp_dir = '/tmp/mapnik-webp/' @@ -45,7 +31,7 @@ def setup(): ] def gen_filepath(name, format): - return os.path.join('images/support/encoding-opts', + return os.path.join('./test/python_tests/images/support/encoding-opts', name + '-' + format.replace(":", "+") + '.webp') def test_quality_threshold(): @@ -54,20 +40,22 @@ def test_quality_threshold(): im.tostring('webp:quality=0') im.tostring('webp:quality=0.001') - @raises(RuntimeError) + def test_quality_threshold_invalid(): im = mapnik.Image(256, 256) - im.tostring('webp:quality=101') + with pytest.raises(RuntimeError): + im.tostring('webp:quality=101') + - @raises(RuntimeError) def test_quality_threshold_invalid2(): im = mapnik.Image(256, 256) - im.tostring('webp:quality=-1') + with pytest.raises(RuntimeError): + im.tostring('webp:quality=-1') - @raises(RuntimeError) def test_quality_threshold_invalid3(): im = mapnik.Image(256, 256) - im.tostring('webp:quality=101.1') + with pytest.raises(RuntimeError): + im.tostring('webp:quality=101.1') generate = os.environ.get('UPDATE') @@ -139,7 +127,7 @@ def test_expected_encodings(): '%s (actual) not == to %s (expected)' % (actual, expected)) # disabled to avoid failures on ubuntu when using old webp packages - # eq_(fails,[],'\n'+'\n'.join(fails)) + # assert fails,[] == '\n'+'\n'.join(fails) except RuntimeError as e: print(e) @@ -175,11 +163,6 @@ def test_transparency_levels(): print( 'warning, cannot open webp expected image (your libwebp is likely too old)') return - eq_(t0_len, len(expected_bytes)) + assert t0_len == len(expected_bytes) except RuntimeError as e: print(e) - - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) From d8a6e05bc56353d8c58e616de36182d0b60a219e Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Fri, 10 Feb 2023 19:16:47 +0000 Subject: [PATCH 17/37] Unite test pycaro [WIP] --- test/python_tests/save_map_test.py | 28 +++----------- test/python_tests/shapeindex_test.py | 22 +++++------ test/python_tests/sqlite_rtree_test.py | 53 ++++++++++---------------- 3 files changed, 36 insertions(+), 67 deletions(-) diff --git a/test/python_tests/save_map_test.py b/test/python_tests/save_map_test.py index 8e7afd21e..f37de4eec 100644 --- a/test/python_tests/save_map_test.py +++ b/test/python_tests/save_map_test.py @@ -1,31 +1,19 @@ -#!/usr/bin/env python - import glob import os import tempfile - -from nose.tools import eq_ - import mapnik +import pytest -from .utilities import execution_path, run_all - +from .utilities import execution_path default_logging_severity = mapnik.logger.get_severity() - +@pytest.fixture(scope="module") def setup(): - # make the tests silent to suppress unsupported params from harfbuzz tests - # TODO: remove this after harfbuzz branch merges - mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) - - -def teardown(): - mapnik.logger.set_severity(default_logging_severity) - + yield def compare_map(xml): m = mapnik.Map(256, 256) @@ -56,7 +44,7 @@ def compare_map(xml): try: with open(test_map) as f1: with open(test_map2) as f2: - eq_(f1.read(), f2.read()) + assert f1.read() == f2.read() except AssertionError as e: raise AssertionError( 'serialized map "%s" not the same after being reloaded, \ncompare with command:\n\n$%s' % @@ -69,7 +57,7 @@ def compare_map(xml): return False -def test_compare_map(): +def test_compare_map(setup): good_maps = glob.glob("../data/good_maps/*.xml") good_maps = [os.path.normpath(p) for p in good_maps] # remove one map that round trips CDATA differently, but this is okay @@ -89,7 +77,3 @@ def test_compare_map_deprecations(): dep = [os.path.normpath(p) for p in dep] for m in dep: compare_map(m) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) diff --git a/test/python_tests/shapeindex_test.py b/test/python_tests/shapeindex_test.py index 53aa04d51..dd526542c 100644 --- a/test/python_tests/shapeindex_test.py +++ b/test/python_tests/shapeindex_test.py @@ -1,24 +1,24 @@ -#!/usr/bin/env python - import fnmatch import os import shutil from subprocess import PIPE, Popen -from nose.tools import eq_ - import mapnik +import pytest -from .utilities import execution_path, run_all - +from .utilities import execution_path +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield + index = '../data/sqlite/world.sqlite.index' + if os.path.exists(index): + os.unlink(index) - -def test_shapeindex(): +def test_shapeindex(setup): # first copy shapefiles to tmp directory source_dir = '../data/shp/' working_dir = '/tmp/mapnik-shp-tmp/' @@ -53,8 +53,4 @@ def test_shapeindex(): count2 = count2 + 1 except StopIteration: pass - eq_(count, count2) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert count == count2 diff --git a/test/python_tests/sqlite_rtree_test.py b/test/python_tests/sqlite_rtree_test.py index 1d4a0abe2..bbe0e8b85 100644 --- a/test/python_tests/sqlite_rtree_test.py +++ b/test/python_tests/sqlite_rtree_test.py @@ -1,27 +1,23 @@ -#!/usr/bin/env python import os import sqlite3 import sys import threading - -from nose.tools import eq_ - import mapnik - -from .utilities import execution_path, run_all - -PYTHON3 = sys.version_info[0] == 3 +import pytest +from .utilities import execution_path +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield + NUM_THREADS = 10 TOTAL = 245 - def create_ds(test_db, table): ds = mapnik.SQLite(file=test_db, table=table) ds.all_features() @@ -29,7 +25,7 @@ def create_ds(test_db, table): if 'sqlite' in mapnik.DatasourceCache.plugin_names(): - def test_rtree_creation(): + def test_rtree_creation(setup): test_db = '../data/sqlite/world.sqlite' index = test_db + '.index' table = 'world_merc' @@ -46,7 +42,7 @@ def test_rtree_creation(): for i in threads: i.join() - eq_(os.path.exists(index), True) + assert os.path.exists(index) conn = sqlite3.connect(index) cur = conn.cursor() try: @@ -55,7 +51,7 @@ def test_rtree_creation(): table.replace( "'", "")) conn.commit() - eq_(cur.fetchone()[0], TOTAL) + assert cur.fetchone()[0] == TOTAL except sqlite3.OperationalError: # don't worry about testing # of index records if # python's sqlite module does not support rtree @@ -66,13 +62,13 @@ def test_rtree_creation(): ds = mapnik.SQLite(file=test_db, table=table) fs = list(ds.all_features()) del ds - eq_(len(fs), TOTAL) + assert len(fs) == TOTAL os.unlink(index) ds = mapnik.SQLite(file=test_db, table=table, use_spatial_index=False) fs = list(ds.all_features()) del ds - eq_(len(fs), TOTAL) - eq_(os.path.exists(index), False) + assert len(fs) == TOTAL + assert os.path.exists(index) == False ds = mapnik.SQLite(file=test_db, table=table, use_spatial_index=True) fs = list(ds.all_features()) @@ -82,10 +78,10 @@ def test_rtree_creation(): # for feat in fs: # query = mapnik.Query(feat.envelope()) # selected = ds.features(query) - # eq_(len(selected.features)>=1,True) + # assert len(selected.features)>=1 == True del ds - eq_(os.path.exists(index), True) + assert os.path.exists(index) == True os.unlink(index) test_rtree_creation.requires_data = True @@ -148,17 +144,17 @@ def make_wkb_point(x, y): # confirm the wkb matches a manually formed wkb wkb2 = make_wkb_point(x, y) - eq_(wkb, wkb2) + assert wkb == wkb2 # ensure we can read this data back out properly with mapnik ds = mapnik.Datasource( **{'type': 'sqlite', 'file': test_db, 'table': 'point_table'}) fs = ds.featureset() feat = fs.next() - eq_(feat.id(), 1) - eq_(feat['name'], 'test point') + assert feat.id() == 1 + assert feat['name'] == 'test point' geom = feat.geometry - eq_(geom.to_wkt(), 'POINT(-122 48)') + assert geom.to_wkt() == 'POINT(-122 48)' del ds # ensure it matches data read with just sqlite @@ -169,19 +165,12 @@ def make_wkb_point(x, y): result = cur.fetchone() cur.close() feat_id = result[0] - eq_(feat_id, 1) + assert feat_id == 1 name = result[2] - eq_(name, 'test point') + assert name == 'test point' geom_wkb_blob = result[1] - if not PYTHON3: - geom_wkb_blob = str(geom_wkb_blob) - eq_(geom_wkb_blob, geom.to_wkb(mapnik.wkbByteOrder.NDR)) + assert geom_wkb_blob == geom.to_wkb(mapnik.wkbByteOrder.NDR) new_geom = mapnik.Geometry.from_wkb(geom_wkb_blob) - eq_(new_geom.to_wkt(), geom.to_wkt()) + assert new_geom.to_wkt() == geom.to_wkt() conn.close() os.unlink(test_db) - -if __name__ == "__main__": - setup() - returncode = run_all(eval(x) for x in dir() if x.startswith("test_")) - exit(returncode) From c79c8371d705b82803532b11761b54f9be5922b2 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 15 Feb 2023 14:25:36 +0000 Subject: [PATCH 18/37] Fix class names to allow pickling support --- mapnik/__init__.py | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/mapnik/__init__.py b/mapnik/__init__.py index 213242632..aec0ce9dc 100644 --- a/mapnik/__init__.py +++ b/mapnik/__init__.py @@ -108,7 +108,7 @@ def __init__(self, *args, **kwargs): Box2d.__init__(self, *args, **kwargs) -class _Coord(Coord, _injector()): +class Coord(_mapnik.Coord, _injector()): """ Represents a point with two coordinates (either lon/lat or x/y). @@ -183,7 +183,7 @@ def inverse(self, projection): return inverse_(self, projection) -class _Box2d(Box2d, _injector()): +class Box2d(_mapnik.Box2d, _injector()): """ Represents a spatial envelope (i.e. bounding box). @@ -238,7 +238,7 @@ def inverse(self, projection): return inverse_(self, projection) -class _Projection(Projection, _injector()): +class Projection(_mapnik.Projection, _injector()): def __repr__(self): return "Projection('%s')" % self.params() @@ -266,15 +266,15 @@ def inverse(self, obj): return inverse_(obj, self) -class _Feature(Feature, _injector()): +class Feature(_mapnik.Feature, _injector()): __geo_interface__ = property(lambda self: json.loads(self.to_geojson())) -class _Geometry(Geometry, _injector()): +class Geometry(_mapnik.Geometry, _injector()): __geo_interface__ = property(lambda self: json.loads(self.to_geojson())) -class _Datasource(Datasource, _injector()): +class Datasource(_mapnik.Datasource, _injector()): def featureset(self, fields = None, variables = {}): query = Query(self.envelope()) @@ -291,13 +291,13 @@ def all_features(self, fields=None, variables={}): return self.__iter__(fields, variables) -class _Color(Color, _injector()): +class Color(_mapnik.Color, _injector()): def __repr__(self): return "Color(R=%d,G=%d,B=%d,A=%d)" % (self.r, self.g, self.b, self.a) -class _SymbolizerBase(SymbolizerBase, _injector()): +class SymbolizerBase(_mapnik.SymbolizerBase, _injector()): # back compatibility @property @@ -804,7 +804,7 @@ def make_it(feat, idx): return itertools.imap(make_it, features, itertools.count(1)) -class _TextSymbolizer(TextSymbolizer, _injector()): +class TextSymbolizer(_mapnik.TextSymbolizer, _injector()): @property def name(self): From 6338188894e8f19f714070e31c339ae2d98ac458 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 15 Feb 2023 14:27:09 +0000 Subject: [PATCH 19/37] Unit tests - pickling test --- test/python_tests/pickling_test.py | 41 ++++++++++++------------------ 1 file changed, 16 insertions(+), 25 deletions(-) diff --git a/test/python_tests/pickling_test.py b/test/python_tests/pickling_test.py index 2b21309b0..61d422403 100644 --- a/test/python_tests/pickling_test.py +++ b/test/python_tests/pickling_test.py @@ -1,34 +1,29 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - import os import pickle - -from nose.tools import eq_ - +import pytest import mapnik +from .utilities import execution_path -from .utilities import execution_path, run_all - - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield -#def test_color_pickle(): -# c = mapnik.Color('blue') -# eq_(pickle.loads(pickle.dumps(c)), c) -# c = mapnik.Color(0, 64, 128) -# eq_(pickle.loads(pickle.dumps(c)), c) -# c = mapnik.Color(0, 64, 128, 192) -# eq_(pickle.loads(pickle.dumps(c)), c) +def test_color_pickle(): + c = mapnik.Color('blue') + assert pickle.loads(pickle.dumps(c)) == c + c = mapnik.Color(0, 64, 128) + assert pickle.loads(pickle.dumps(c)) == c + c = mapnik.Color(0, 64, 128, 192) + assert pickle.loads(pickle.dumps(c)) == c -#def test_envelope_pickle(): -# e = mapnik.Box2d(100, 100, 200, 200) -# eq_(pickle.loads(pickle.dumps(e)), e) +def test_envelope_pickle(): + e = mapnik.Box2d(100, 100, 200, 200) + assert pickle.loads(pickle.dumps(e)) == e def test_parameters_pickle(): @@ -37,9 +32,5 @@ def test_parameters_pickle(): params2 = pickle.loads(pickle.dumps(params, pickle.HIGHEST_PROTOCOL)) - eq_(params[0][0], params2[0][0]) - eq_(params[0][1], params2[0][1]) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert params[0][0] == params2[0][0] + assert params[0][1] == params2[0][1] From b872f14df3dc8522679ad29ea8c78b509500bc96 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 15 Feb 2023 14:54:24 +0000 Subject: [PATCH 20/37] Unit test - remove 'osm' plugin test --- test/python_tests/osm_test.py | 69 ----------------------------------- 1 file changed, 69 deletions(-) delete mode 100644 test/python_tests/osm_test.py diff --git a/test/python_tests/osm_test.py b/test/python_tests/osm_test.py deleted file mode 100644 index ef39f4ab5..000000000 --- a/test/python_tests/osm_test.py +++ /dev/null @@ -1,69 +0,0 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import os - -from nose.tools import eq_ - -import mapnik - -from .utilities import execution_path, run_all - - -def setup(): - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - -if 'osm' in mapnik.DatasourceCache.plugin_names(): - - # osm initialization - def test_osm_init(): - ds = mapnik.Osm(file='../data/osm/nodes.osm') - - e = ds.envelope() - - # these are hardcoded in the plugin… ugh - eq_(e.minx >= -180.0, True) - eq_(e.miny >= -90.0, True) - eq_(e.maxx <= 180.0, True) - eq_(e.maxy <= 90, True) - - def test_that_nonexistant_query_field_throws(**kwargs): - ds = mapnik.Osm(file='../data/osm/nodes.osm') - eq_(len(ds.fields()), 0) - query = mapnik.Query(ds.envelope()) - for fld in ds.fields(): - query.add_property_name(fld) - # also add an invalid one, triggering throw - query.add_property_name('bogus') - ds.features(query) - - def test_that_64bit_int_fields_work(): - ds = mapnik.Osm(file='../data/osm/64bit.osm') - eq_(len(ds.fields()), 4) - eq_(ds.fields(), ['bigint', 'highway', 'junction', 'note']) - eq_(ds.field_types(), ['str', 'str', 'str', 'str']) - fs = ds.featureset() - feat = fs.next() - eq_(feat.to_geojson( - ), '{"type":"Feature","id":890,"geometry":{"type":"Point","coordinates":[-61.7960248,17.1415874]},"properties":{}}') - eq_(feat.id(), 4294968186) - eq_(feat['bigint'], None) - feat = fs.next() - eq_(feat['bigint'], '9223372036854775807') - - def test_reading_ways(): - ds = mapnik.Osm(file='../data/osm/ways.osm') - eq_(len(ds.fields()), 0) - eq_(ds.fields(), []) - eq_(ds.field_types(), []) - feat = ds.all_features()[4] - eq_(feat.to_geojson( - ), '{"type":"Feature","id":1,"geometry":{"type":"LineString","coordinates":[[0,2],[0,-2]]},"properties":{}}') - eq_(feat.id(), 1) - - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) From af89241fb7d6ac37da81edc684827a3bdac6fab9 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 15 Feb 2023 15:08:56 +0000 Subject: [PATCH 21/37] Unit test - png encoding/suite [WIP] --- test/python_tests/png_encoding_test.py | 98 ++++++++------------------ test/python_tests/pngsuite_test.py | 24 +++---- 2 files changed, 38 insertions(+), 84 deletions(-) diff --git a/test/python_tests/png_encoding_test.py b/test/python_tests/png_encoding_test.py index 8916f0f14..92858b1a4 100644 --- a/test/python_tests/png_encoding_test.py +++ b/test/python_tests/png_encoding_test.py @@ -1,15 +1,9 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - import os - -from nose.tools import eq_ - import mapnik +import pytest +from .utilities import execution_path -from .utilities import execution_path, run_all - - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() @@ -47,7 +41,7 @@ def gen_filepath(name, format): generate = os.environ.get('UPDATE') - def test_expected_encodings(): + def test_expected_encodings(setup): # blank image im = mapnik.Image(256, 256) for opt in opts: @@ -58,9 +52,7 @@ def test_expected_encodings(): im.save(expected, opt) else: im.save(actual, opt) - eq_(mapnik.Image.open(actual).tostring('png32'), - mapnik.Image.open(expected).tostring('png32'), - '%s (actual) not == to %s (expected)' % (actual, expected)) + assert mapnik.Image.open(actual).tostring('png32') == mapnik.Image.open(expected).tostring('png32'), '%s (actual) not == to %s (expected)' % (actual, expected) # solid image im.fill(mapnik.Color('green')) @@ -72,9 +64,7 @@ def test_expected_encodings(): im.save(expected, opt) else: im.save(actual, opt) - eq_(mapnik.Image.open(actual).tostring('png32'), - mapnik.Image.open(expected).tostring('png32'), - '%s (actual) not == to %s (expected)' % (actual, expected)) + assert mapnik.Image.open(actual).tostring('png32') == mapnik.Image.open(expected).tostring('png32'), '%s (actual) not == to %s (expected)' % (actual, expected) # aerial im = mapnik.Image.open('./images/support/transparency/aerial_rgba.png') @@ -86,9 +76,7 @@ def test_expected_encodings(): im.save(expected, opt) else: im.save(actual, opt) - eq_(mapnik.Image.open(actual).tostring('png32'), - mapnik.Image.open(expected).tostring('png32'), - '%s (actual) not == to %s (expected)' % (actual, expected)) + assert mapnik.Image.open(actual).tostring('png32') == mapnik.Image.open(expected).tostring('png32'), '%s (actual) not == to %s (expected)' % (actual, expected) def test_transparency_levels(): # create partial transparency image @@ -112,100 +100,83 @@ def test_transparency_levels(): im.save(t0, format) im_in = mapnik.Image.open(t0) t0_len = len(im_in.tostring(format)) - eq_(t0_len, len(mapnik.Image.open( - 'images/support/transparency/white0.png').tostring(format))) + assert t0_len == len(mapnik.Image.open('images/support/transparency/white0.png').tostring(format)) format = 'png8:m=o:t=1' im.save(t1, format) im_in = mapnik.Image.open(t1) t1_len = len(im_in.tostring(format)) - eq_(len(im.tostring(format)), len(mapnik.Image.open( - 'images/support/transparency/white1.png').tostring(format))) + assert len(im.tostring(format)) == len(mapnik.Image.open('images/support/transparency/white1.png').tostring(format)) format = 'png8:m=o:t=2' im.save(t2, format) im_in = mapnik.Image.open(t2) t2_len = len(im_in.tostring(format)) - eq_(len(im.tostring(format)), len(mapnik.Image.open( - 'images/support/transparency/white2.png').tostring(format))) - - eq_(t0_len < t1_len < t2_len, True) + assert len(im.tostring(format)) == len(mapnik.Image.open('images/support/transparency/white2.png').tostring(format)) + assert t0_len < t1_len < t2_len # hextree format = 'png8:m=h:t=0' im.save(t0, format) im_in = mapnik.Image.open(t0) t0_len = len(im_in.tostring(format)) - eq_(t0_len, len(mapnik.Image.open( - 'images/support/transparency/white0.png').tostring(format))) + assert t0_len == len(mapnik.Image.open('images/support/transparency/white0.png').tostring(format)) format = 'png8:m=h:t=1' im.save(t1, format) im_in = mapnik.Image.open(t1) t1_len = len(im_in.tostring(format)) - eq_(len(im.tostring(format)), len(mapnik.Image.open( - 'images/support/transparency/white1.png').tostring(format))) + assert len(im.tostring(format)) == len(mapnik.Image.open('images/support/transparency/white1.png').tostring(format)) format = 'png8:m=h:t=2' im.save(t2, format) im_in = mapnik.Image.open(t2) t2_len = len(im_in.tostring(format)) - eq_(len(im.tostring(format)), len(mapnik.Image.open( - 'images/support/transparency/white2.png').tostring(format))) - - eq_(t0_len < t1_len < t2_len, True) + assert len(im.tostring(format)) == len(mapnik.Image.open('images/support/transparency/white2.png').tostring(format)) + assert t0_len < t1_len < t2_len def test_transparency_levels_aerial(): im = mapnik.Image.open('../data/images/12_654_1580.png') im_in = mapnik.Image.open( './images/support/transparency/aerial_rgba.png') - eq_(len(im.tostring('png8')), len(im_in.tostring('png8'))) - eq_(len(im.tostring('png32')), len(im_in.tostring('png32'))) + assert len(im.tostring('png8')) == len(im_in.tostring('png8')) + assert len(im.tostring('png32')) == len(im_in.tostring('png32')) im_in = mapnik.Image.open( './images/support/transparency/aerial_rgb.png') - eq_(len(im.tostring('png32')), len(im_in.tostring('png32'))) - eq_(len(im.tostring('png32:t=0')), len(im_in.tostring('png32:t=0'))) - eq_(len(im.tostring('png32:t=0')) == len(im_in.tostring('png32')), False) - eq_(len(im.tostring('png8')), len(im_in.tostring('png8'))) - eq_(len(im.tostring('png8:t=0')), len(im_in.tostring('png8:t=0'))) + assert len(im.tostring('png32')) == len(im_in.tostring('png32')) + assert len(im.tostring('png32:t=0')) == len(im_in.tostring('png32:t=0')) + assert not len(im.tostring('png32:t=0')) == len(im_in.tostring('png32')) + assert len(im.tostring('png8')) == len(im_in.tostring('png8')) + assert len(im.tostring('png8:t=0')) == len(im_in.tostring('png8:t=0')) # unlike png32 paletted images without alpha will look the same even if # no alpha is forced - eq_(len(im.tostring('png8:t=0')) == len(im_in.tostring('png8')), True) - eq_(len(im.tostring('png8:t=0:m=o')) == - len(im_in.tostring('png8:m=o')), True) + assert len(im.tostring('png8:t=0')) == len(im_in.tostring('png8')) + assert len(im.tostring('png8:t=0:m=o')) == len(im_in.tostring('png8:m=o')) def test_9_colors_hextree(): expected = './images/support/encoding-opts/png8-9cols.png' im = mapnik.Image.open(expected) t0 = tmp_dir + 'png-encoding-9-colors.result-hextree.png' im.save(t0, 'png8:m=h') - eq_(mapnik.Image.open(t0).tostring(), - mapnik.Image.open(expected).tostring(), - '%s (actual) not == to %s (expected)' % (t0, expected)) + assert mapnik.Image.open(t0).tostring() == mapnik.Image.open(expected).tostring(), '%s (actual) not == to %s (expected)' % (t0, expected) def test_9_colors_octree(): expected = './images/support/encoding-opts/png8-9cols.png' im = mapnik.Image.open(expected) t0 = tmp_dir + 'png-encoding-9-colors.result-octree.png' im.save(t0, 'png8:m=o') - eq_(mapnik.Image.open(t0).tostring(), - mapnik.Image.open(expected).tostring(), - '%s (actual) not == to %s (expected)' % (t0, expected)) + assert mapnik.Image.open(t0).tostring() == mapnik.Image.open(expected).tostring(), '%s (actual) not == to %s (expected)' % (t0, expected) def test_17_colors_hextree(): expected = './images/support/encoding-opts/png8-17cols.png' im = mapnik.Image.open(expected) t0 = tmp_dir + 'png-encoding-17-colors.result-hextree.png' im.save(t0, 'png8:m=h') - eq_(mapnik.Image.open(t0).tostring(), - mapnik.Image.open(expected).tostring(), - '%s (actual) not == to %s (expected)' % (t0, expected)) + assert mapnik.Image.open(t0).tostring() == mapnik.Image.open(expected).tostring(), '%s (actual) not == to %s (expected)' % (t0, expected) def test_17_colors_octree(): expected = './images/support/encoding-opts/png8-17cols.png' im = mapnik.Image.open(expected) t0 = tmp_dir + 'png-encoding-17-colors.result-octree.png' im.save(t0, 'png8:m=o') - eq_(mapnik.Image.open(t0).tostring(), - mapnik.Image.open(expected).tostring(), - '%s (actual) not == to %s (expected)' % (t0, expected)) + assert mapnik.Image.open(t0).tostring() == mapnik.Image.open(expected).tostring(), '%s (actual) not == to %s (expected)' % (t0, expected) def test_2px_regression_hextree(): im = mapnik.Image.open('./images/support/encoding-opts/png8-2px.A.png') @@ -213,20 +184,11 @@ def test_2px_regression_hextree(): t0 = tmp_dir + 'png-encoding-2px.result-hextree.png' im.save(t0, 'png8:m=h') - eq_(mapnik.Image.open(t0).tostring(), - mapnik.Image.open(expected).tostring(), - '%s (actual) not == to %s (expected)' % (t0, expected)) + assert mapnik.Image.open(t0).tostring() == mapnik.Image.open(expected).tostring(), '%s (actual) not == to %s (expected)' % (t0, expected) def test_2px_regression_octree(): im = mapnik.Image.open('./images/support/encoding-opts/png8-2px.A.png') expected = './images/support/encoding-opts/png8-2px.png' t0 = tmp_dir + 'png-encoding-2px.result-octree.png' im.save(t0, 'png8:m=o') - eq_(mapnik.Image.open(t0).tostring(), - mapnik.Image.open(expected).tostring(), - '%s (actual) not == to %s (expected)' % (t0, expected)) - - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert mapnik.Image.open(t0).tostring() == mapnik.Image.open(expected).tostring(), '%s (actual) not == to %s (expected)' % (t0, expected) diff --git a/test/python_tests/pngsuite_test.py b/test/python_tests/pngsuite_test.py index 8ce517f49..2f773578d 100644 --- a/test/python_tests/pngsuite_test.py +++ b/test/python_tests/pngsuite_test.py @@ -1,16 +1,11 @@ -#!/usr/bin/env python - import os - -from nose.tools import assert_raises - import mapnik - -from .utilities import execution_path, run_all +import pytest +from .utilities import execution_path datadir = '../data/pngsuite' - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() @@ -18,7 +13,8 @@ def setup(): def assert_broken_file(fname): - assert_raises(RuntimeError, lambda: mapnik.Image.open(fname)) + with pytest.raises(RuntimeError): + mapnik.Image.open(fname) def assert_good_file(fname): @@ -31,15 +27,11 @@ def get_pngs(good): for x in files if good != x.startswith('x')] -def test_good_pngs(): +def test_good_pngs(setup): for x in get_pngs(True): - yield assert_good_file, x + assert_good_file, x def test_broken_pngs(): for x in get_pngs(False): - yield assert_broken_file, x - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert_broken_file, x From 5dacb7234b345507d54927a55633d57f33a11b85 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Wed, 15 Feb 2023 15:09:47 +0000 Subject: [PATCH 22/37] remove unused definition --- src/mapnik_symbolizer.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/src/mapnik_symbolizer.cpp b/src/mapnik_symbolizer.cpp index 286b11af1..72e29e403 100644 --- a/src/mapnik_symbolizer.cpp +++ b/src/mapnik_symbolizer.cpp @@ -198,7 +198,6 @@ boost::python::object __getitem__(mapnik::symbolizer_base const& sym, std::strin boost::python::object symbolizer_keys(mapnik::symbolizer_base const& sym) { - using const_iterator = symbolizer_base::cont_type::const_iterator; boost::python::list keys; for (auto const& kv : sym.properties) { From 60aadccbb8a3642c5494c0b578dbbcb64c7515fa Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Fri, 17 Feb 2023 10:18:43 +0000 Subject: [PATCH 23/37] Add missing converter for mapnik::path_expression_ptr --- src/mapnik_symbolizer.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/mapnik_symbolizer.cpp b/src/mapnik_symbolizer.cpp index 72e29e403..f98079126 100644 --- a/src/mapnik_symbolizer.cpp +++ b/src/mapnik_symbolizer.cpp @@ -255,6 +255,7 @@ void export_symbolizer() implicitly_convertible(); implicitly_convertible(); implicitly_convertible(); + implicitly_convertible(); implicitly_convertible(); implicitly_convertible, mapnik::symbolizer_base::value_type>(); From 73b4904658da21ce1e71be7079753c29a0bb19dc Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Fri, 17 Feb 2023 12:45:04 +0000 Subject: [PATCH 24/37] Unit tests - upgrade all to `pytest` + fix paths logic setup.py - use pkg_config to setup 'cairo' paths + bump min macOS to 13 --- setup.py | 12 +- test/python_tests/cairo_test.py | 24 +- test/python_tests/compositing_test.py | 76 +- test/python_tests/csv_test.py | 34 +- test/python_tests/datasource_test.py | 31 +- .../datasource_xml_template_test.py | 14 +- test/python_tests/extra_map_props_test.py | 15 +- test/python_tests/feature_id_test.py | 25 +- test/python_tests/fontset_test.py | 16 +- test/python_tests/geojson_plugin_test.py | 26 +- test/python_tests/image_filters_test.py | 16 +- test/python_tests/image_test.py | 14 +- test/python_tests/image_tiff_test.py | 38 +- test/python_tests/introspection_test.py | 21 +- test/python_tests/layer_buffer_size_test.py | 20 +- test/python_tests/layer_modification_test.py | 17 +- test/python_tests/load_map_test.py | 17 +- test/python_tests/map_query_test.py | 23 +- test/python_tests/mapnik_test_data_test.py | 30 +- .../markers_complex_rendering_test.py | 33 +- test/python_tests/multi_tile_raster_test.py | 15 +- test/python_tests/object_test.py | 753 ++++++------------ .../ogr_and_shape_geometries_test.py | 14 +- test/python_tests/ogr_test.py | 30 +- test/python_tests/palette_test.py | 21 +- test/python_tests/pdf_printing_test.py | 15 +- test/python_tests/pgraster_test.py | 18 +- test/python_tests/png_encoding_test.py | 1 + test/python_tests/pngsuite_test.py | 2 +- test/python_tests/projection_test.py | 87 +- test/python_tests/query_test.py | 43 +- test/python_tests/query_tolerance_test.py | 26 +- test/python_tests/raster_colorizer_test.py | 56 +- test/python_tests/raster_symbolizer_test.py | 39 +- test/python_tests/rasterlite_test.py | 30 +- test/python_tests/render_grid_test.py | 14 +- test/python_tests/render_test.py | 22 +- test/python_tests/reprojection_test.py | 45 +- test/python_tests/shapefile_test.py | 31 +- test/python_tests/topojson_plugin_test.py | 27 +- test/python_tests/utilities.py | 18 +- 41 files changed, 794 insertions(+), 1015 deletions(-) diff --git a/setup.py b/setup.py index 9985da5a2..4b12c4c8a 100755 --- a/setup.py +++ b/setup.py @@ -7,6 +7,8 @@ import subprocess import sys import glob +import pkg_resources + from distutils import sysconfig from ctypes.util import find_library @@ -230,19 +232,21 @@ def run(self): if os.environ.get("PYCAIRO", "false") == "true": try: extra_comp_args.append('-DHAVE_PYCAIRO') - print("-I%s/include/pycairo".format(sys.exec_prefix)) - extra_comp_args.append("-I{0}/include/pycairo".format(sys.exec_prefix)) + dist = pkg_resources.get_distribution('pycairo') + print(dist.location) + print("-I%s/cairo/include".format(dist.location)) + extra_comp_args.append("-I{0}/cairo/include".format(dist.location)) #extra_comp_args.extend(check_output(["pkg-config", '--cflags', 'pycairo']).strip().split(' ')) #linkflags.extend(check_output(["pkg-config", '--libs', 'pycairo']).strip().split(' ')) except: raise Exception("Failed to find compiler options for pycairo") if sys.platform == 'darwin': - extra_comp_args.append('-mmacosx-version-min=10.11') + extra_comp_args.append('-mmacosx-version-min=13.0') # silence warning coming from boost python macros which # would is hard to silence via pragma extra_comp_args.append('-Wno-parentheses-equality') - linkflags.append('-mmacosx-version-min=10.11') + linkflags.append('-mmacosx-version-min=13.0') else: linkflags.append('-lrt') linkflags.append('-Wl,-z,origin') diff --git a/test/python_tests/cairo_test.py b/test/python_tests/cairo_test.py index a296a91a2..a3d324314 100644 --- a/test/python_tests/cairo_test.py +++ b/test/python_tests/cairo_test.py @@ -1,6 +1,16 @@ import os import shutil import mapnik +import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + def make_tmp_map(): m = mapnik.Map(512, 512) @@ -75,12 +85,12 @@ def cairo_color(c): if mapnik.has_pycairo(): import cairo - def test_passing_pycairo_context_svg(): + def test_passing_pycairo_context_svg(setup): m = make_tmp_map() m.zoom_to_box(mapnik.Box2d(-180, -90, 180, 90)) test_cairo_file = '/tmp/mapnik-cairo-context-test.svg' surface = cairo.SVGSurface(test_cairo_file, m.width, m.height) - expected_cairo_file = './test/python_tests/images/pycairo/cairo-cairo-expected.svg' + expected_cairo_file = 'images/pycairo/cairo-cairo-expected.svg' context = cairo.Context(surface) mapnik.render(m, context) draw_title(m, context, "Hello Map", size=20) @@ -102,7 +112,7 @@ def test_passing_pycairo_context_pdf(): m.zoom_to_box(mapnik.Box2d(-180, -90, 180, 90)) test_cairo_file = '/tmp/mapnik-cairo-context-test.pdf' surface = cairo.PDFSurface(test_cairo_file, m.width, m.height) - expected_cairo_file = './test/python_tests/images/pycairo/cairo-cairo-expected.pdf' + expected_cairo_file = 'images/pycairo/cairo-cairo-expected.pdf' context = cairo.Context(surface) mapnik.render(m, context) draw_title(m, context, "Hello Map", size=20) @@ -124,8 +134,8 @@ def test_passing_pycairo_context_png(): m.zoom_to_box(mapnik.Box2d(-180, -90, 180, 90)) test_cairo_file = '/tmp/mapnik-cairo-context-test.png' surface = cairo.ImageSurface(cairo.FORMAT_ARGB32, m.width, m.height) - expected_cairo_file = './test/python_tests/images/pycairo/cairo-cairo-expected.png' - expected_cairo_file2 = './test/python_tests/images/pycairo/cairo-cairo-expected-reduced.png' + expected_cairo_file = 'images/pycairo/cairo-cairo-expected.png' + expected_cairo_file2 = 'images/pycairo/cairo-cairo-expected-reduced.png' context = cairo.Context(surface) mapnik.render(m, context) draw_title(m, context, "Hello Map", size=20) @@ -163,10 +173,10 @@ def test_passing_pycairo_context_png(): def _pycairo_surface(type, sym): test_cairo_file = '/tmp/mapnik-cairo-surface-test.%s.%s' % ( sym, type) - expected_cairo_file = './test/python_tests/images/pycairo/cairo-surface-expected.%s.%s' % ( + expected_cairo_file = 'images/pycairo/cairo-surface-expected.%s.%s' % ( sym, type) m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/%s_symbolizer.xml' % sym) + mapnik.load_map(m, '../data/good_maps/%s_symbolizer.xml' % sym) m.zoom_all() if hasattr(cairo, '%sSurface' % type.upper()): surface = getattr( diff --git a/test/python_tests/compositing_test.py b/test/python_tests/compositing_test.py index ac09ef9ad..1356dbf97 100644 --- a/test/python_tests/compositing_test.py +++ b/test/python_tests/compositing_test.py @@ -1,22 +1,14 @@ -# encoding: utf8 - -from __future__ import print_function - import os - -from nose.tools import eq_ - import mapnik +import pytest +from .utilities import (get_unique_colors, pixel2channels, side_by_side_image, execution_path) -from .utilities import (execution_path, get_unique_colors, pixel2channels, - run_all, side_by_side_image) - - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) - + yield def is_pre(color, alpha): return (color * 255.0 / alpha) <= 255 @@ -93,14 +85,14 @@ def validate_pixels_are_premultiplied(image): return (num_bad == 0, bad_pixels) -def test_compare_images(): - b = mapnik.Image.open('./images/support/b.png') +def test_compare_images(setup): + b = mapnik.Image.open('images/support/b.png') b.premultiply() num_ops = len(mapnik.CompositeOp.names) successes = [] fails = [] for name in mapnik.CompositeOp.names: - a = mapnik.Image.open('./images/support/a.png') + a = mapnik.Image.open('images/support/a.png') a.premultiply() a.composite(b, getattr(mapnik.CompositeOp, name)) actual = '/tmp/mapnik-comp-op-test-' + name + '.png' @@ -132,53 +124,53 @@ def test_compare_images(): name + '.fail.png', 'png32') - eq_(len(successes), num_ops, '\n' + '\n'.join(fails)) + assert len(successes) == num_ops, '\n' + '\n'.join(fails) b.demultiply() # b will be slightly modified by pre and then de multiplication rounding errors # TODO - write test to ensure the image is 99% the same. #expected_b = mapnik.Image.open('./images/support/b.png') # b.save('/tmp/mapnik-comp-op-test-original-mask.png') - #eq_(b.tostring('png32'),expected_b.tostring('png32'), '/tmp/mapnik-comp-op-test-original-mask.png is no longer equivalent to original mask: ./images/support/b.png') + #assert b.tostring('png32') == expected_b.tostring('png32'), '/tmp/mapnik-comp-op-test-original-mask.png is no longer equivalent to original mask: ./images/support/b.png' def test_pre_multiply_status(): - b = mapnik.Image.open('./images/support/b.png') + b = mapnik.Image.open('images/support/b.png') # not premultiplied yet, should appear that way result = validate_pixels_are_not_premultiplied(b) - eq_(result, True) + assert result # not yet premultiplied therefore should return false result = validate_pixels_are_premultiplied(b) - eq_(result[0], False) + assert not result[0] # now actually premultiply the pixels b.premultiply() # now checking if premultiplied should succeed result = validate_pixels_are_premultiplied(b) - eq_(result[0], True) + assert result[0] # should now not appear to look not premultiplied result = validate_pixels_are_not_premultiplied(b) - eq_(result, False) + assert not result # now actually demultiply the pixels b.demultiply() # should now appear demultiplied result = validate_pixels_are_not_premultiplied(b) - eq_(result, True) + assert result def test_pre_multiply_status_of_map1(): m = mapnik.Map(256, 256) im = mapnik.Image(m.width, m.height) - eq_(validate_pixels_are_not_premultiplied(im), True) + assert validate_pixels_are_not_premultiplied(im) mapnik.render(m, im) - eq_(validate_pixels_are_not_premultiplied(im), True) + assert validate_pixels_are_not_premultiplied(im) def test_pre_multiply_status_of_map2(): m = mapnik.Map(256, 256) m.background = mapnik.Color(1, 1, 1, 255) im = mapnik.Image(m.width, m.height) - eq_(validate_pixels_are_not_premultiplied(im), True) + assert validate_pixels_are_not_premultiplied(im) mapnik.render(m, im) - eq_(validate_pixels_are_not_premultiplied(im), True) + assert validate_pixels_are_not_premultiplied(im) if 'shape' in mapnik.DatasourceCache.plugin_names(): def test_style_level_comp_op(): @@ -215,7 +207,7 @@ def test_style_level_comp_op(): name + '.fail.png', 'png32') - eq_(len(fails), 0, '\n' + '\n'.join(fails)) + assert len(fails) == 0, '\n' + '\n'.join(fails) def test_style_level_opacity(): m = mapnik.Map(512, 512) @@ -228,10 +220,8 @@ def test_style_level_opacity(): expected = 'images/support/mapnik-style-level-opacity.png' im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'tests/python_tests/' + expected)) + assert im.tostring('png32') == expected_im.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual, + 'tests/python_tests/' + expected) def test_rounding_and_color_expectations(): @@ -239,24 +229,24 @@ def test_rounding_and_color_expectations(): m.background = mapnik.Color('rgba(255,255,255,.4999999)') im = mapnik.Image(m.width, m.height) mapnik.render(m, im) - eq_(get_unique_colors(im), ['rgba(255,255,255,127)']) + assert get_unique_colors(im) == ['rgba(255,255,255,127)'] m = mapnik.Map(1, 1) m.background = mapnik.Color('rgba(255,255,255,.5)') im = mapnik.Image(m.width, m.height) mapnik.render(m, im) - eq_(get_unique_colors(im), ['rgba(255,255,255,128)']) + assert get_unique_colors(im) == ['rgba(255,255,255,128)'] im_file = mapnik.Image.open('../data/images/stripes_pattern.png') - eq_(get_unique_colors(im_file), ['rgba(0,0,0,0)', 'rgba(74,74,74,255)']) + assert get_unique_colors(im_file) == ['rgba(0,0,0,0)', 'rgba(74,74,74,255)'] # should have no effect im_file.premultiply() - eq_(get_unique_colors(im_file), ['rgba(0,0,0,0)', 'rgba(74,74,74,255)']) + assert get_unique_colors(im_file) == ['rgba(0,0,0,0)', 'rgba(74,74,74,255)'] im_file.apply_opacity(.5) # should have effect now that image has transparency im_file.premultiply() - eq_(get_unique_colors(im_file), ['rgba(0,0,0,0)', 'rgba(37,37,37,127)']) + assert get_unique_colors(im_file) == ['rgba(0,0,0,0)', 'rgba(37,37,37,127)'] # should restore to original nonpremultiplied colors im_file.demultiply() - eq_(get_unique_colors(im_file), ['rgba(0,0,0,0)', 'rgba(74,74,74,127)']) + assert get_unique_colors(im_file) == ['rgba(0,0,0,0)', 'rgba(74,74,74,127)'] def test_background_image_and_background_color(): @@ -265,7 +255,7 @@ def test_background_image_and_background_color(): m.background_image = '../data/images/stripes_pattern.png' im = mapnik.Image(m.width, m.height) mapnik.render(m, im) - eq_(get_unique_colors(im), ['rgba(255,255,255,128)', 'rgba(74,74,74,255)']) + assert get_unique_colors(im) == ['rgba(255,255,255,128)', 'rgba(74,74,74,255)'] def test_background_image_with_alpha_and_background_color(): @@ -274,7 +264,7 @@ def test_background_image_with_alpha_and_background_color(): m.background_image = '../data/images/yellow_half_trans.png' im = mapnik.Image(m.width, m.height) mapnik.render(m, im) - eq_(get_unique_colors(im), ['rgba(255,255,85,191)']) + assert get_unique_colors(im) == ['rgba(255,255,85,191)'] def test_background_image_with_alpha_and_background_color_against_composited_control(): @@ -295,8 +285,4 @@ def test_background_image_with_alpha_and_background_color_against_composited_con # compare image rendered (compositing in `agg_renderer::setup`) # vs image composited via python bindings #raise Todo("looks like we need to investigate PNG color rounding when saving") - # eq_(get_unique_colors(im),get_unique_colors(im1)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert get_unique_colors(im) == get_unique_colors(im1) diff --git a/test/python_tests/csv_test.py b/test/python_tests/csv_test.py index 07c681cfa..2d8528067 100644 --- a/test/python_tests/csv_test.py +++ b/test/python_tests/csv_test.py @@ -2,19 +2,27 @@ import os import mapnik import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield if 'csv' in mapnik.DatasourceCache.plugin_names(): def get_csv_ds(filename): return mapnik.Datasource( - type='csv', file=os.path.join('./test/data/csv/', filename)) + type='csv', file=os.path.join('../data/csv/', filename)) - def test_broken_files(visual=False): - broken = glob.glob("./test/data/csv/fails/*.*") - broken.extend(glob.glob("./test/data/csv/warns/*.*")) + def test_broken_files(setup, visual=False): + broken = glob.glob("../data/csv/fails/*.*") + broken.extend(glob.glob("../data/csv/warns/*.*")) # Add a filename that doesn't exist - broken.append("./test/data/csv/fails/does_not_exist.csv") + broken.append("../data/csv/fails/does_not_exist.csv") for csv in broken: if visual: @@ -24,10 +32,10 @@ def test_broken_files(visual=False): except Exception: print('\x1b[1;32m✓ \x1b[0m', csv) - def test_good_files(visual=False): - good_files = glob.glob("./test/data/csv/*.*") - good_files.extend(glob.glob("./test/data/csv/warns/*.*")) - ignorable = os.path.join('./test', 'data', 'csv', 'long_lat.vrt') + def test_good_files(setup, visual=False): + good_files = glob.glob("../data/csv/*.*") + good_files.extend(glob.glob("../data/csv/warns/*.*")) + ignorable = os.path.join('..', 'data', 'csv', 'long_lat.vrt') print("ignorable:", ignorable) good_files.remove(ignorable) for f in good_files: @@ -469,7 +477,7 @@ def test_that_fewer_headers_than_rows_throws(**kwargs): def test_that_feature_id_only_incremented_for_valid_rows(**kwargs): ds = mapnik.Datasource(type='csv', - file=os.path.join('./test/data/csv/warns', 'feature_id_counting.csv')) + file=os.path.join('../data/csv/warns', 'feature_id_counting.csv')) assert len(ds.fields()) == 3 assert ds.fields(), ['x', 'y' == 'id'] assert ds.field_types(), ['int', 'int' == 'int'] @@ -491,7 +499,7 @@ def test_that_feature_id_only_incremented_for_valid_rows(**kwargs): def test_dynamically_defining_headers1(**kwargs): ds = mapnik.Datasource(type='csv', file=os.path.join( - './test/data/csv/fails', 'needs_headers_two_lines.csv'), + '../data/csv/fails', 'needs_headers_two_lines.csv'), headers='x,y,name') assert len(ds.fields()) == 3 assert ds.fields(), ['x', 'y' == 'name'] @@ -508,7 +516,7 @@ def test_dynamically_defining_headers1(**kwargs): def test_dynamically_defining_headers2(**kwargs): ds = mapnik.Datasource(type='csv', file=os.path.join( - './test/data/csv/fails', 'needs_headers_one_line.csv'), + '../data/csv/fails', 'needs_headers_one_line.csv'), headers='x,y,name') assert len(ds.fields()) == 3 assert ds.fields(), ['x', 'y' == 'name'] @@ -525,7 +533,7 @@ def test_dynamically_defining_headers2(**kwargs): def test_dynamically_defining_headers3(**kwargs): ds = mapnik.Datasource(type='csv', file=os.path.join( - './test/data/csv/fails', 'needs_headers_one_line_no_newline.csv'), + '../data/csv/fails', 'needs_headers_one_line_no_newline.csv'), headers='x,y,name') assert len(ds.fields()) == 3 assert ds.fields(), ['x', 'y' == 'name'] diff --git a/test/python_tests/datasource_test.py b/test/python_tests/datasource_test.py index 5fa6780c6..5c9e85d76 100644 --- a/test/python_tests/datasource_test.py +++ b/test/python_tests/datasource_test.py @@ -2,21 +2,28 @@ import sys import mapnik import pytest - +from .utilities import execution_path from itertools import groupby +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + def test_that_datasources_exist(): if len(mapnik.DatasourceCache.plugin_names()) == 0: print('***NOTICE*** - no datasource plugins have been loaded') # adapted from raster_symboliser_test#test_dataraster_query_point -def test_vrt_referring_to_missing_files(): +def test_vrt_referring_to_missing_files(setup): with pytest.raises(RuntimeError): srs = 'epsg:32630' if 'gdal' in mapnik.DatasourceCache.plugin_names(): lyr = mapnik.Layer('dataraster') lyr.datasource = mapnik.Gdal( - file='./test/data/raster/missing_raster.vrt', + file='../data/raster/missing_raster.vrt', band=1, ) lyr.srs = srs @@ -51,7 +58,7 @@ def test_vrt_referring_to_missing_files(): def test_field_listing(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') + ds = mapnik.Shapefile(file='../data/shp/poly.shp') fields = ds.fields() assert fields, ['AREA', 'EAS_ID' == 'PRFEDEA'] desc = ds.describe() @@ -63,14 +70,14 @@ def test_field_listing(): def test_total_feature_count_shp(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') + ds = mapnik.Shapefile(file='../data/shp/poly.shp') features = ds.all_features() num_feats = len(list(features)) assert num_feats == 10 def test_total_feature_count_json(): if 'ogr' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Ogr(file='./test/data/json/points.geojson', layer_by_index=0) + ds = mapnik.Ogr(file='../data/json/points.geojson', layer_by_index=0) desc = ds.describe() assert desc['geometry_type'] == mapnik.DataGeometryType.Point assert desc['name'] == 'ogr' @@ -84,7 +91,7 @@ def test_total_feature_count_json(): def test_sqlite_reading(): if 'sqlite' in mapnik.DatasourceCache.plugin_names(): ds = mapnik.SQLite( - file='./test/data/sqlite/world.sqlite', + file='../data/sqlite/world.sqlite', table_by_index=0) desc = ds.describe() assert desc['geometry_type'] == mapnik.DataGeometryType.Polygon @@ -97,7 +104,7 @@ def test_sqlite_reading(): def test_reading_json_from_string(): - with open('./test/data/json/points.geojson', 'r') as f: + with open('../data/json/points.geojson', 'r') as f: json = f.read() if 'ogr' in mapnik.DatasourceCache.plugin_names(): ds = mapnik.Ogr(file=json, layer_by_index=0) @@ -108,7 +115,7 @@ def test_reading_json_from_string(): def test_feature_envelope(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') + ds = mapnik.Shapefile(file='../data/shp/poly.shp') features = ds.all_features() for feat in features: env = feat.envelope() @@ -120,7 +127,7 @@ def test_feature_envelope(): def test_feature_attributes(): if 'shape' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Shapefile(file='./test/data/shp/poly.shp') + ds = mapnik.Shapefile(file='../data/shp/poly.shp') features = list(ds.all_features()) feat = features[0] attrs = {'PRFEDEA': u'35043411', 'EAS_ID': 168, 'AREA': 215229.266} @@ -131,7 +138,7 @@ def test_feature_attributes(): def test_ogr_layer_by_sql(): if 'ogr' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Ogr(file='./test/data/shp/poly.shp', + ds = mapnik.Ogr(file='../data/shp/poly.shp', layer_by_sql='SELECT * FROM poly WHERE EAS_ID = 168') features = ds.all_features() num_feats = len(list(features)) @@ -147,7 +154,7 @@ def rle_encode(l): m = mapnik.Map(256, 256) try: - mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') + mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') m.zoom_all() join_field = 'NAME' fg = [] # feature grid diff --git a/test/python_tests/datasource_xml_template_test.py b/test/python_tests/datasource_xml_template_test.py index 1a0c06131..6c5de3587 100644 --- a/test/python_tests/datasource_xml_template_test.py +++ b/test/python_tests/datasource_xml_template_test.py @@ -1,8 +1,18 @@ +import os import mapnik +import pytest +from .utilities import execution_path -def test_datasource_template_is_working(): +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + +def test_datasource_template_is_working(setup): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/datasource.xml') + mapnik.load_map(m, '../data/good_maps/datasource.xml') for layer in m.layers: layer_bbox = layer.envelope() bbox = None diff --git a/test/python_tests/extra_map_props_test.py b/test/python_tests/extra_map_props_test.py index 1b8796763..b774561bb 100644 --- a/test/python_tests/extra_map_props_test.py +++ b/test/python_tests/extra_map_props_test.py @@ -1,8 +1,19 @@ +import os import mapnik +import pytest +from .utilities import execution_path -def test_arbitrary_parameters_attached_to_map(): +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + + +def test_arbitrary_parameters_attached_to_map(setup): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/extra_arbitary_map_parameters.xml') + mapnik.load_map(m, '../data/good_maps/extra_arbitary_map_parameters.xml') assert len(m.parameters) == 5 assert m.parameters['key'] == 'value2' assert m.parameters['key3'] == 'value3' diff --git a/test/python_tests/feature_id_test.py b/test/python_tests/feature_id_test.py index 4f64b06ee..66faa9f4b 100644 --- a/test/python_tests/feature_id_test.py +++ b/test/python_tests/feature_id_test.py @@ -1,10 +1,19 @@ import mapnik - +import os +import pytest try: import itertools.izip as zip except ImportError: pass +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield def compare_shape_between_mapnik_and_ogr(shapefile, query=None): plugins = mapnik.DatasourceCache.plugin_names() @@ -24,23 +33,23 @@ def compare_shape_between_mapnik_and_ogr(shapefile, query=None): return True -def test_shapefile_line_featureset_id(): - compare_shape_between_mapnik_and_ogr('./test/data/shp/polylines.shp') +def test_shapefile_line_featureset_id(setup): + compare_shape_between_mapnik_and_ogr('../data/shp/polylines.shp') def test_shapefile_polygon_featureset_id(): - compare_shape_between_mapnik_and_ogr('./test/data/shp/poly.shp') + compare_shape_between_mapnik_and_ogr('../data/shp/poly.shp') def test_shapefile_polygon_feature_query_id(): bbox = (15523428.2632, 4110477.6323, -11218494.8310, 7495720.7404) query = mapnik.Query(mapnik.Box2d(*bbox)) if 'ogr' in mapnik.DatasourceCache.plugin_names(): - ds = mapnik.Ogr(file='./test/data/shp/world_merc.shp', layer_by_index=0) + ds = mapnik.Ogr(file='../data/shp/world_merc.shp', layer_by_index=0) for fld in ds.fields(): query.add_property_name(fld) compare_shape_between_mapnik_and_ogr( - './test/data/shp/world_merc.shp', query) + '../data/shp/world_merc.shp', query) def test_feature_hit_count(): @@ -49,10 +58,10 @@ def test_feature_hit_count(): bbox = (1113194.91,4512803.085,2226389.82,6739192.905) query = mapnik.Query(mapnik.Box2d(*bbox)) if 'ogr' in mapnik.DatasourceCache.plugin_names(): - ds1 = mapnik.Ogr(file='./test/data/shp/world_merc.shp',layer_by_index=0) + ds1 = mapnik.Ogr(file='../data/shp/world_merc.shp',layer_by_index=0) for fld in ds1.fields(): query.add_property_name(fld) - ds2 = mapnik.Shapefile(file='./test/data/shp/world_merc.shp') + ds2 = mapnik.Shapefile(file='../data/shp/world_merc.shp') count1 = len(list(ds1.features(query))) count2 = len(list(ds2.features(query))) assert count1 < count2 # expected 17 and 20 diff --git a/test/python_tests/fontset_test.py b/test/python_tests/fontset_test.py index 3fb01dce0..72915e67d 100644 --- a/test/python_tests/fontset_test.py +++ b/test/python_tests/fontset_test.py @@ -1,8 +1,20 @@ +import os import mapnik +import pytest -def test_loading_fontset_from_map(): +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + + +def test_loading_fontset_from_map(setup): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/fontset.xml', True) + mapnik.load_map(m, '../data/good_maps/fontset.xml', True) fs = m.find_fontset('book-fonts') assert len(fs.names) == 2 assert list(fs.names) == ['DejaVu Sans Book', 'DejaVu Sans Oblique'] diff --git a/test/python_tests/geojson_plugin_test.py b/test/python_tests/geojson_plugin_test.py index 557ef242a..8670954b9 100644 --- a/test/python_tests/geojson_plugin_test.py +++ b/test/python_tests/geojson_plugin_test.py @@ -1,12 +1,22 @@ +import os import mapnik import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + if 'geojson' in mapnik.DatasourceCache.plugin_names(): - def test_geojson_init(): + def test_geojson_init(setup): ds = mapnik.Datasource( type='geojson', - file='./test/data/json/escaped.geojson') + file='../data/json/escaped.geojson') e = ds.envelope() assert e.minx == pytest.approx(-81.705583, abs=1e-7) assert e.miny == pytest.approx(41.480573, abs=1e-6) @@ -16,7 +26,7 @@ def test_geojson_init(): def test_geojson_properties(): ds = mapnik.Datasource( type='geojson', - file='./test/data/json/escaped.geojson') + file='../data/json/escaped.geojson') f = list(ds.features_at_point(ds.envelope().center()))[0] assert len(ds.fields()) == 11 desc = ds.describe() @@ -33,7 +43,7 @@ def test_geojson_properties(): ds = mapnik.Datasource( type='geojson', - file='./test/data/json/escaped.geojson') + file='../data/json/escaped.geojson') f = list(ds.all_features())[0] assert len(ds.fields()) == 11 @@ -52,7 +62,7 @@ def test_geojson_properties(): def test_large_geojson_properties(): ds = mapnik.Datasource( type='geojson', - file='./test/data/json/escaped.geojson', + file='../data/json/escaped.geojson', cache_features=False) f = list(ds.features_at_point(ds.envelope().center()))[0] assert len(ds.fields()) == 11 @@ -70,7 +80,7 @@ def test_large_geojson_properties(): ds = mapnik.Datasource( type='geojson', - file='./test/data/json/escaped.geojson') + file='../data/json/escaped.geojson') f = list(ds.all_features())[0] assert len(ds.fields()) == 11 @@ -103,7 +113,7 @@ def test_geojson_from_in_memory_string(): def test_that_nonexistant_query_field_throws(**kwargs): ds = mapnik.Datasource( type='geojson', - file='./test/data/json/escaped.geojson') + file='../data/json/escaped.geojson') assert len(ds.fields()) == 11 # TODO - this sorting is messed up #assert ds.fields(),['name', 'int', 'double', 'description', 'boolean' == 'NOM_FR'] @@ -119,7 +129,7 @@ def test_that_nonexistant_query_field_throws(**kwargs): def test_parsing_feature_collection_with_top_level_properties(): ds = mapnik.Datasource( type='geojson', - file='./test/data/json/feature_collection_level_properties.json') + file='../data/json/feature_collection_level_properties.json') f = list(ds.all_features())[0] desc = ds.describe() diff --git a/test/python_tests/image_filters_test.py b/test/python_tests/image_filters_test.py index c61da73d6..5c5002f59 100644 --- a/test/python_tests/image_filters_test.py +++ b/test/python_tests/image_filters_test.py @@ -1,6 +1,14 @@ import re, os import mapnik -from .utilities import side_by_side_image +import pytest +from .utilities import side_by_side_image, execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield def replace_style(m, name, style): m.remove_style(name) @@ -15,9 +23,9 @@ def test_append(): assert s.image_filters == 'sharpen' if 'shape' in mapnik.DatasourceCache.plugin_names(): - def test_style_level_image_filter(): + def test_style_level_image_filter(setup): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/style_level_image_filter.xml') + mapnik.load_map(m, '../data/good_maps/style_level_image_filter.xml') m.zoom_all() successes = [] fails = [] @@ -39,7 +47,7 @@ def test_style_level_image_filter(): im = mapnik.Image(m.width, m.height) mapnik.render(m, im) actual = '/tmp/mapnik-style-image-filter-' + filename + '.png' - expected = './test/python_tests/images/style-image-filter/' + filename + '.png' + expected = 'images/style-image-filter/' + filename + '.png' im.save(actual, "png32") if not os.path.exists(expected) or os.environ.get('UPDATE'): print('generating expected test image: %s' % expected) diff --git a/test/python_tests/image_test.py b/test/python_tests/image_test.py index ba758b5af..da4b3a757 100644 --- a/test/python_tests/image_test.py +++ b/test/python_tests/image_test.py @@ -1,9 +1,17 @@ +import os import mapnik import pytest -from .utilities import READ_FLAGS, get_unique_colors +from .utilities import READ_FLAGS, get_unique_colors, execution_path -def test_type(): +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + +def test_type(setup): im = mapnik.Image(256, 256) assert im.get_type() == mapnik.ImageType.rgba8 im = mapnik.Image(256, 256, mapnik.ImageType.gray8) @@ -352,7 +360,7 @@ def test_png_round_trip(): def test_image_open_from_string(): - filepath = './test/data/images/dummy.png' + filepath = '../data/images/dummy.png' im1 = mapnik.Image.open(filepath) with open(filepath, READ_FLAGS) as f: im2 = mapnik.Image.fromstring(f.read()) diff --git a/test/python_tests/image_tiff_test.py b/test/python_tests/image_tiff_test.py index c5fcc395f..0a2373645 100644 --- a/test/python_tests/image_tiff_test.py +++ b/test/python_tests/image_tiff_test.py @@ -1,12 +1,20 @@ +import os import hashlib import mapnik +import pytest +from .utilities import READ_FLAGS, execution_path -from .utilities import READ_FLAGS +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield def hashstr(var): return hashlib.md5(var).hexdigest() -def test_tiff_round_trip_scanline(): +def test_tiff_round_trip_scanline(setup): filepath = '/tmp/mapnik-tiff-io-scanline.tiff' im = mapnik.Image(255, 267) im.fill(mapnik.Color('rgba(12,255,128,.5)')) @@ -170,7 +178,7 @@ def test_tiff_round_trip_tiled(): def test_tiff_rgb8_compare(): - filepath1 = './test/data/tiff/ndvi_256x256_rgb8_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_rgb8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgb8.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff') @@ -184,7 +192,7 @@ def test_tiff_rgb8_compare(): def test_tiff_rgba8_compare_scanline(): - filepath1 = './test/data/tiff/ndvi_256x256_rgba8_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_rgba8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgba8-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') @@ -198,7 +206,7 @@ def test_tiff_rgba8_compare_scanline(): def test_tiff_rgba8_compare_stripped(): - filepath1 = './test/data/tiff/ndvi_256x256_rgba8_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_rgba8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgba8-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') @@ -212,7 +220,7 @@ def test_tiff_rgba8_compare_stripped(): def test_tiff_rgba8_compare_tiled(): - filepath1 = './test/data/tiff/ndvi_256x256_rgba8_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_rgba8_striped.tif' filepath2 = '/tmp/mapnik-tiff-rgba8-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') @@ -226,7 +234,7 @@ def test_tiff_rgba8_compare_tiled(): def test_tiff_gray8_compare_scanline(): - filepath1 = './test/data/tiff/ndvi_256x256_gray8_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray8_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray8-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') @@ -239,7 +247,7 @@ def test_tiff_gray8_compare_scanline(): assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray8).tostring("tiff")) def test_tiff_gray8_compare_stripped(): - filepath1 = './test/data/tiff/ndvi_256x256_gray8_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray8_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray8-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') @@ -253,7 +261,7 @@ def test_tiff_gray8_compare_stripped(): def test_tiff_gray8_compare_tiled(): - filepath1 = './test/data/tiff/ndvi_256x256_gray8_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray8_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray8-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') @@ -267,7 +275,7 @@ def test_tiff_gray8_compare_tiled(): def test_tiff_gray16_compare_scanline(): - filepath1 = './test/data/tiff/ndvi_256x256_gray16_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray16_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray16-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') @@ -280,7 +288,7 @@ def test_tiff_gray16_compare_scanline(): assert hashstr(im.tostring("tiff")) != hashstr(mapnik.Image(im.width(), im.height(), mapnik.ImageType.gray16).tostring("tiff")) def test_tiff_gray16_compare_stripped(): - filepath1 = './test/data/tiff/ndvi_256x256_gray16_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray16_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray16-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') @@ -294,7 +302,7 @@ def test_tiff_gray16_compare_stripped(): def test_tiff_gray16_compare_tiled(): - filepath1 = './test/data/tiff/ndvi_256x256_gray16_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray16_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray16-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') @@ -308,7 +316,7 @@ def test_tiff_gray16_compare_tiled(): def test_tiff_gray32f_compare_scanline(): - filepath1 = './test/data/tiff/ndvi_256x256_gray32f_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray32f_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray32f-scanline.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=scanline') @@ -322,7 +330,7 @@ def test_tiff_gray32f_compare_scanline(): def test_tiff_gray32f_compare_stripped(): - filepath1 = './test/data/tiff/ndvi_256x256_gray32f_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray32f_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray32f-stripped.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=stripped') @@ -336,7 +344,7 @@ def test_tiff_gray32f_compare_stripped(): def test_tiff_gray32f_compare_tiled(): - filepath1 = './test/data/tiff/ndvi_256x256_gray32f_striped.tif' + filepath1 = '../data/tiff/ndvi_256x256_gray32f_striped.tif' filepath2 = '/tmp/mapnik-tiff-gray32f-tiled.tiff' im = mapnik.Image.open(filepath1) im.save(filepath2, 'tiff:method=tiled') diff --git a/test/python_tests/introspection_test.py b/test/python_tests/introspection_test.py index 215be7d3f..2986eb906 100644 --- a/test/python_tests/introspection_test.py +++ b/test/python_tests/introspection_test.py @@ -1,21 +1,32 @@ +import os import mapnik +import pytest -def test_introspect_symbolizers(): +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + +def test_introspect_symbolizers(setup): # create a symbolizer p = mapnik.PointSymbolizer() - p.file = "./test/data/images/dummy.png" + p.file = "../data/images/dummy.png" p.allow_overlap = True p.opacity = 0.5 assert p.allow_overlap == True assert p.opacity == 0.5 - assert p.filename == './test/data/images/dummy.png' + assert p.filename == '../data/images/dummy.png' # make sure the defaults # are what we think they are assert p.allow_overlap == True assert p.opacity == 0.5 - assert p.filename == './test/data/images/dummy.png' + assert p.filename == '../data/images/dummy.png' # contruct objects to hold it r = mapnik.Rule() @@ -43,4 +54,4 @@ def test_introspect_symbolizers(): assert p2.allow_overlap == True assert p2.opacity == 0.5 - assert p2.filename == './test/data/images/dummy.png' + assert p2.filename == '../data/images/dummy.png' diff --git a/test/python_tests/layer_buffer_size_test.py b/test/python_tests/layer_buffer_size_test.py index 093fe7221..41f3528f9 100644 --- a/test/python_tests/layer_buffer_size_test.py +++ b/test/python_tests/layer_buffer_size_test.py @@ -1,22 +1,32 @@ +import os import mapnik +import pytest + +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield if 'sqlite' in mapnik.DatasourceCache.plugin_names(): # the negative buffer on the layer should # override the postive map buffer leading # only one point to be rendered in the map - def test_layer_buffer_size_1(): + def test_layer_buffer_size_1(setup): m = mapnik.Map(512, 512) assert m.buffer_size == 0 - mapnik.load_map(m, './test/data/good_maps/layer_buffer_size_reduction.xml') + mapnik.load_map(m, '../data/good_maps/layer_buffer_size_reduction.xml') assert m.buffer_size == 256 assert m.layers[0].buffer_size == -150 m.zoom_all() im = mapnik.Image(m.width, m.height) mapnik.render(m, im) actual = '/tmp/mapnik-layer-buffer-size.png' - expected = './test/python_tests/images/support/mapnik-layer-buffer-size.png' + expected = 'images/support/mapnik-layer-buffer-size.png' im.save(actual, "png32") expected_im = mapnik.Image.open(expected) - assert im.tostring('png32') == expected_im.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual, - 'tests/python_tests/' + expected) + assert im.tostring('png32') == expected_im.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual,'tests/python_tests/' + expected) diff --git a/test/python_tests/layer_modification_test.py b/test/python_tests/layer_modification_test.py index 37ac73ed1..bf01d634c 100644 --- a/test/python_tests/layer_modification_test.py +++ b/test/python_tests/layer_modification_test.py @@ -1,6 +1,17 @@ +import os import mapnik +import pytest -def test_adding_datasource_to_layer(): +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + +def test_adding_datasource_to_layer(setup): map_string = ''' @@ -10,7 +21,7 @@ def test_adding_datasource_to_layer(): @@ -42,7 +53,7 @@ def test_adding_datasource_to_layer(): assert lyr.srs == 'epsg:4326' # now add a datasource one... - ds = mapnik.Shapefile(file='./test/data/shp/world_merc.shp') + ds = mapnik.Shapefile(file='../data/shp/world_merc.shp') m.layers[0].datasource = ds # now ensure it is attached diff --git a/test/python_tests/load_map_test.py b/test/python_tests/load_map_test.py index 85d23f8ac..d9e0c3345 100644 --- a/test/python_tests/load_map_test.py +++ b/test/python_tests/load_map_test.py @@ -1,12 +1,23 @@ -import glob +import glob,os import mapnik +import pytest + +from .utilities import execution_path default_logging_severity = mapnik.logger.get_severity() -def teardown(): +@pytest.fixture(scope="module") +def setup_and_teardown(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + # make the tests silent to suppress unsupported params from harfbuzz tests + # TODO: remove this after harfbuzz branch merges + mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) + yield mapnik.logger.set_severity(default_logging_severity) -def test_broken_files(): +def test_broken_files(setup_and_teardown): default_logging_severity = mapnik.logger.get_severity() mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) broken_files = glob.glob("../data/broken_maps/*.xml") diff --git a/test/python_tests/map_query_test.py b/test/python_tests/map_query_test.py index 268f7fbf3..78b3da213 100644 --- a/test/python_tests/map_query_test.py +++ b/test/python_tests/map_query_test.py @@ -1,8 +1,17 @@ +import os import mapnik import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield # map has no layers -def test_map_query_throw1(): +def test_map_query_throw1(setup): with pytest.raises(IndexError): m = mapnik.Map(256, 256) m.zoom_to_box(mapnik.Box2d(-1, -1, 0, 0)) @@ -25,20 +34,20 @@ def test_map_query_throw3(): def test_map_query_throw4(): with pytest.raises(RuntimeError): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') + mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') m.query_point(0, 0, 0) # invalid coords in general (do not intersect) def test_map_query_throw5(): with pytest.raises(RuntimeError): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') + mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') m.zoom_all() m.query_point(0, 9999999999999999, 9999999999999999) def test_map_query_works1(): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/wgs842merc_reprojection.xml') + mapnik.load_map(m, '../data/good_maps/wgs842merc_reprojection.xml') merc_bounds = mapnik.Box2d(-20037508.34, - 20037508.34, 20037508.34, 20037508.34) m.maximum_extent = merc_bounds @@ -50,7 +59,7 @@ def test_map_query_works1(): def test_map_query_works2(): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/merc2wgs84_reprojection.xml') + mapnik.load_map(m, '../data/good_maps/merc2wgs84_reprojection.xml') wgs84_bounds = mapnik.Box2d(-179.999999975, - 85.0511287776, 179.999999975, 85.0511287776) m.maximum_extent = wgs84_bounds @@ -69,7 +78,7 @@ def test_map_query_works2(): def test_map_query_in_pixels_works1(): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/wgs842merc_reprojection.xml') + mapnik.load_map(m, '../data/good_maps/wgs842merc_reprojection.xml') merc_bounds = mapnik.Box2d(-20037508.34, - 20037508.34, 20037508.34, 20037508.34) m.maximum_extent = merc_bounds @@ -80,7 +89,7 @@ def test_map_query_in_pixels_works1(): def test_map_query_in_pixels_works2(): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/merc2wgs84_reprojection.xml') + mapnik.load_map(m, '../data/good_maps/merc2wgs84_reprojection.xml') wgs84_bounds = mapnik.Box2d(-179.999999975, - 85.0511287776, 179.999999975, 85.0511287776) m.maximum_extent = wgs84_bounds diff --git a/test/python_tests/mapnik_test_data_test.py b/test/python_tests/mapnik_test_data_test.py index c0efff684..a75306e74 100644 --- a/test/python_tests/mapnik_test_data_test.py +++ b/test/python_tests/mapnik_test_data_test.py @@ -1,29 +1,7 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -from __future__ import print_function - -import os +import os from glob import glob - import mapnik -from .utilities import execution_path, run_all - - -default_logging_severity = mapnik.logger.get_severity() - - -def setup(): - mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) - # All of the paths used are relative, if we run the tests - # from another directory we need to chdir() - os.chdir(execution_path('.')) - - -def teardown(): - mapnik.logger.set_severity(default_logging_severity) - plugin_mapping = { '.csv': ['csv'], '.json': ['geojson', 'ogr'], @@ -55,7 +33,7 @@ def test_opening_data(): else: for plugin in plugin_mapping[ext]: kwargs = {'type': plugin, 'file': filepath} - if plugin is 'ogr': + if plugin == 'ogr': kwargs['layer_by_index'] = 0 try: mapnik.Datasource(**kwargs) @@ -63,7 +41,3 @@ def test_opening_data(): print('could not open, %s: %s' % (kwargs, e)) # else: # print 'skipping opening %s' % filepath - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) diff --git a/test/python_tests/markers_complex_rendering_test.py b/test/python_tests/markers_complex_rendering_test.py index 652c4ac22..bd1473cb1 100644 --- a/test/python_tests/markers_complex_rendering_test.py +++ b/test/python_tests/markers_complex_rendering_test.py @@ -1,35 +1,29 @@ -# coding=utf8 -import os - -from nose.tools import eq_ - +import pytest import mapnik +import os +from .utilities import execution_path -from .utilities import execution_path, run_all - - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield if 'csv' in mapnik.DatasourceCache.plugin_names(): - def test_marker_ellipse_render1(): + def test_marker_ellipse_render1(setup): m = mapnik.Map(256, 256) mapnik.load_map(m, '../data/good_maps/marker_ellipse_transform.xml') m.zoom_all() im = mapnik.Image(m.width, m.height) mapnik.render(m, im) actual = '/tmp/mapnik-marker-ellipse-render1.png' - expected = 'images/support/mapnik-marker-ellipse-render1.png' + expected = './images/support/mapnik-marker-ellipse-render1.png' im.save(actual, 'png32') if os.environ.get('UPDATE'): im.save(expected, 'png32') expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected)) + assert im.tostring('png32') == expected_im.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual, expected) def test_marker_ellipse_render2(): m = mapnik.Map(256, 256) @@ -38,16 +32,9 @@ def test_marker_ellipse_render2(): im = mapnik.Image(m.width, m.height) mapnik.render(m, im) actual = '/tmp/mapnik-marker-ellipse-render2.png' - expected = 'images/support/mapnik-marker-ellipse-render2.png' + expected = './images/support/mapnik-marker-ellipse-render2.png' im.save(actual, 'png32') if os.environ.get('UPDATE'): im.save(expected, 'png32') expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im.tostring('png32') == expected_im.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual, expected) diff --git a/test/python_tests/multi_tile_raster_test.py b/test/python_tests/multi_tile_raster_test.py index 5ec750dcd..facda1c57 100644 --- a/test/python_tests/multi_tile_raster_test.py +++ b/test/python_tests/multi_tile_raster_test.py @@ -1,11 +1,22 @@ +import os import mapnik +import pytest +from .utilities import execution_path -def test_multi_tile_policy(): +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + + +def test_multi_tile_policy(setup): srs = 'epsg:4326' lyr = mapnik.Layer('raster') if 'raster' in mapnik.DatasourceCache.plugin_names(): lyr.datasource = mapnik.Raster( - file='./test/data/raster_tiles/${x}/${y}.tif', + file='../data/raster_tiles/${x}/${y}.tif', lox=-180, loy=-90, hix=180, diff --git a/test/python_tests/object_test.py b/test/python_tests/object_test.py index a972d416d..21699d45a 100644 --- a/test/python_tests/object_test.py +++ b/test/python_tests/object_test.py @@ -1,570 +1,275 @@ -# #!/usr/bin/env python -# # -*- coding: utf-8 -*- - -# import os -# from nose.tools import * -# from utilities import execution_path, run_all -# import tempfile - -# import mapnik - -# def setup(): -# # All of the paths used are relative, if we run the tests -# # from another directory we need to chdir() -# os.chdir(execution_path('.')) - -# def test_debug_symbolizer(): -# s = mapnik.DebugSymbolizer() -# eq_(s.mode,mapnik.debug_symbolizer_mode.collision) - -# def test_raster_symbolizer(): -# s = mapnik.RasterSymbolizer() -# eq_(s.comp_op,mapnik.CompositeOp.src_over) # note: mode is deprecated -# eq_(s.scaling,mapnik.scaling_method.NEAR) -# eq_(s.opacity,1.0) -# eq_(s.colorizer,None) -# eq_(s.filter_factor,-1) -# eq_(s.mesh_size,16) -# eq_(s.premultiplied,None) -# s.premultiplied = True -# eq_(s.premultiplied,True) - -# def test_line_pattern(): -# s = mapnik.LinePatternSymbolizer(mapnik.PathExpression('../data/images/dummy.png')) -# eq_(s.filename, '../data/images/dummy.png') -# eq_(s.smooth,0.0) -# eq_(s.transform,'') -# eq_(s.offset,0.0) -# eq_(s.comp_op,mapnik.CompositeOp.src_over) -# eq_(s.clip,True) - -# def test_line_symbolizer(): -# s = mapnik.LineSymbolizer() -# eq_(s.rasterizer, mapnik.line_rasterizer.FULL) -# eq_(s.smooth,0.0) -# eq_(s.comp_op,mapnik.CompositeOp.src_over) -# eq_(s.clip,True) -# eq_(s.stroke.width, 1) -# eq_(s.stroke.opacity, 1) -# eq_(s.stroke.color, mapnik.Color('black')) -# eq_(s.stroke.line_cap, mapnik.line_cap.BUTT_CAP) -# eq_(s.stroke.line_join, mapnik.line_join.MITER_JOIN) - -# l = mapnik.LineSymbolizer(mapnik.Color('blue'), 5.0) - -# eq_(l.stroke.width, 5) -# eq_(l.stroke.opacity, 1) -# eq_(l.stroke.color, mapnik.Color('blue')) -# eq_(l.stroke.line_cap, mapnik.line_cap.BUTT_CAP) -# eq_(l.stroke.line_join, mapnik.line_join.MITER_JOIN) - -# s = mapnik.Stroke(mapnik.Color('blue'), 5.0) -# l = mapnik.LineSymbolizer(s) - -# eq_(l.stroke.width, 5) -# eq_(l.stroke.opacity, 1) -# eq_(l.stroke.color, mapnik.Color('blue')) -# eq_(l.stroke.line_cap, mapnik.line_cap.BUTT_CAP) -# eq_(l.stroke.line_join, mapnik.line_join.MITER_JOIN) - -# def test_line_symbolizer_stroke_reference(): -# l = mapnik.LineSymbolizer(mapnik.Color('green'),0.1) -# l.stroke.add_dash(.1,.1) -# l.stroke.add_dash(.1,.1) -# eq_(l.stroke.get_dashes(), [(.1,.1),(.1,.1)]) -# eq_(l.stroke.color,mapnik.Color('green')) -# eq_(l.stroke.opacity,1.0) -# assert_almost_equal(l.stroke.width,0.1) - -# # https://github.com/mapnik/mapnik/issues/1427 -# def test_stroke_dash_api(): -# stroke = mapnik.Stroke() -# dashes = [(1.0,1.0)] -# stroke.dasharray = dashes -# eq_(stroke.dasharray, dashes) -# stroke.add_dash(.1,.1) -# dashes.append((.1,.1)) -# eq_(stroke.dasharray, dashes) - - -# def test_text_symbolizer(): -# s = mapnik.TextSymbolizer() -# eq_(s.comp_op,mapnik.CompositeOp.src_over) -# eq_(s.clip,True) -# eq_(s.halo_rasterizer,mapnik.halo_rasterizer.FULL) - -# # https://github.com/mapnik/mapnik/issues/1420 -# eq_(s.text_transform, mapnik.text_transform.NONE) - -# # old args required method -# ts = mapnik.TextSymbolizer(mapnik.Expression('[Field_Name]'), 'Font Name', 8, mapnik.Color('black')) -# # eq_(str(ts.name), str(mapnik2.Expression('[Field_Name]'))) name field is no longer supported -# eq_(ts.format.face_name, 'Font Name') -# eq_(ts.format.text_size, 8) -# eq_(ts.format.fill, mapnik.Color('black')) -# eq_(ts.properties.label_placement, mapnik.label_placement.POINT_PLACEMENT) -# eq_(ts.properties.horizontal_alignment, mapnik.horizontal_alignment.AUTO) - -# def test_shield_symbolizer_init(): -# s = mapnik.ShieldSymbolizer(mapnik.Expression('[Field Name]'), 'DejaVu Sans Bold', 6, mapnik.Color('#000000'), mapnik.PathExpression('../data/images/dummy.png')) -# eq_(s.comp_op,mapnik.CompositeOp.src_over) -# eq_(s.clip,True) -# eq_(s.displacement, (0.0,0.0)) -# eq_(s.allow_overlap, False) -# eq_(s.avoid_edges, False) -# eq_(s.character_spacing,0) -# #eq_(str(s.name), str(mapnik2.Expression('[Field Name]'))) name field is no longer supported -# eq_(s.face_name, 'DejaVu Sans Bold') -# eq_(s.allow_overlap, False) -# eq_(s.fill, mapnik.Color('#000000')) -# eq_(s.halo_fill, mapnik.Color('rgb(255,255,255)')) -# eq_(s.halo_radius, 0) -# eq_(s.label_placement, mapnik.label_placement.POINT_PLACEMENT) -# eq_(s.minimum_distance, 0.0) -# eq_(s.text_ratio, 0) -# eq_(s.text_size, 6) -# eq_(s.wrap_width, 0) -# eq_(s.vertical_alignment, mapnik.vertical_alignment.AUTO) -# eq_(s.label_spacing, 0) -# eq_(s.label_position_tolerance, 0) -# # 22.5 * M_PI/180.0 initialized by default -# assert_almost_equal(s.max_char_angle_delta, 0.39269908169872414) - -# eq_(s.text_transform, mapnik.text_transform.NONE) -# eq_(s.line_spacing, 0) -# eq_(s.character_spacing, 0) - -# # r1341 -# eq_(s.wrap_before, False) -# eq_(s.horizontal_alignment, mapnik.horizontal_alignment.AUTO) -# eq_(s.justify_alignment, mapnik.justify_alignment.AUTO) -# eq_(s.opacity, 1.0) - -# # r2300 -# eq_(s.minimum_padding, 0.0) - -# # was mixed with s.opacity -# eq_(s.text_opacity, 1.0) - -# eq_(s.shield_displacement, (0.0,0.0)) -# # TODO - the pattern in bindings seems to be to get/set -# # strings for PathExpressions... should we pass objects? -# eq_(s.filename, '../data/images/dummy.png') - -# # 11c34b1: default transform list is empty, not identity matrix -# eq_(s.transform, '') - -# eq_(s.fontset, None) - -# # ShieldSymbolizer missing image file -# # images paths are now PathExpressions are evaluated at runtime -# # so it does not make sense to throw... -# #@raises(RuntimeError) -# #def test_shieldsymbolizer_missing_image(): -# # s = mapnik.ShieldSymbolizer(mapnik.Expression('[Field Name]'), 'DejaVu Sans Bold', 6, mapnik.Color('#000000'), mapnik.PathExpression('../#data/images/broken.png')) - -# def test_shield_symbolizer_modify(): -# s = mapnik.ShieldSymbolizer(mapnik.Expression('[Field Name]'), 'DejaVu Sans Bold', 6, mapnik.Color('#000000'), mapnik.PathExpression('../data/images/dummy.png')) -# # transform expression -# def check_transform(expr, expect_str=None): -# s.transform = expr -# eq_(s.transform, expr if expect_str is None else expect_str) -# check_transform("matrix(1 2 3 4 5 6)", "matrix(1, 2, 3, 4, 5, 6)") -# check_transform("matrix(1, 2, 3, 4, 5, 6 +7)", "matrix(1, 2, 3, 4, 5, (6+7))") -# check_transform("rotate([a])") -# check_transform("rotate([a] -2)", "rotate(([a]-2))") -# check_transform("rotate([a] -2 -3)", "rotate([a], -2, -3)") -# check_transform("rotate([a] -2 -3 -4)", "rotate(((([a]-2)-3)-4))") -# check_transform("rotate([a] -2, 3, 4)", "rotate(([a]-2), 3, 4)") -# check_transform("translate([tx]) rotate([a])") -# check_transform("scale([sx], [sy]/2)") -# # TODO check expected failures - -# def test_point_symbolizer(): -# p = mapnik.PointSymbolizer() -# eq_(p.filename,'') -# eq_(p.transform,'') -# eq_(p.opacity,1.0) -# eq_(p.allow_overlap,False) -# eq_(p.ignore_placement,False) -# eq_(p.comp_op,mapnik.CompositeOp.src_over) -# eq_(p.placement, mapnik.point_placement.CENTROID) - -# p = mapnik.PointSymbolizer(mapnik.PathExpression("../data/images/dummy.png")) -# p.allow_overlap = True -# p.opacity = 0.5 -# p.ignore_placement = True -# p.placement = mapnik.point_placement.INTERIOR -# eq_(p.allow_overlap, True) -# eq_(p.opacity, 0.5) -# eq_(p.filename,'../data/images/dummy.png') -# eq_(p.ignore_placement,True) -# eq_(p.placement, mapnik.point_placement.INTERIOR) - -# def test_markers_symbolizer(): -# p = mapnik.MarkersSymbolizer() -# eq_(p.allow_overlap, False) -# eq_(p.opacity,1.0) -# eq_(p.fill_opacity,None) -# eq_(p.filename,'shape://ellipse') -# eq_(p.placement,mapnik.marker_placement.POINT_PLACEMENT) -# eq_(p.multi_policy,mapnik.marker_multi_policy.EACH) -# eq_(p.fill,None) -# eq_(p.ignore_placement,False) -# eq_(p.spacing,100) -# eq_(p.max_error,0.2) -# eq_(p.width,None) -# eq_(p.height,None) -# eq_(p.transform,'') -# eq_(p.clip,True) -# eq_(p.comp_op,mapnik.CompositeOp.src_over) - - -# p.width = mapnik.Expression('12') -# p.height = mapnik.Expression('12') -# eq_(str(p.width),'12') -# eq_(str(p.height),'12') - -# p.width = mapnik.Expression('[field] + 2') -# p.height = mapnik.Expression('[field] + 2') -# eq_(str(p.width),'([field]+2)') -# eq_(str(p.height),'([field]+2)') - -# stroke = mapnik.Stroke() -# stroke.color = mapnik.Color('black') -# stroke.width = 1.0 - -# p.stroke = stroke -# p.fill = mapnik.Color('white') -# p.allow_overlap = True -# p.opacity = 0.5 -# p.fill_opacity = 0.5 -# p.placement = mapnik.marker_placement.LINE_PLACEMENT -# p.multi_policy = mapnik.marker_multi_policy.WHOLE - -# eq_(p.allow_overlap, True) -# eq_(p.opacity, 0.5) -# eq_(p.fill_opacity, 0.5) -# eq_(p.multi_policy,mapnik.marker_multi_policy.WHOLE) -# eq_(p.placement,mapnik.marker_placement.LINE_PLACEMENT) - -# #https://github.com/mapnik/mapnik/issues/1285 -# #https://github.com/mapnik/mapnik/issues/1427 -# p.marker_type = 'arrow' -# eq_(p.marker_type,'shape://arrow') -# eq_(p.filename,'shape://arrow') - - -# # PointSymbolizer missing image file -# # images paths are now PathExpressions are evaluated at runtime -# # so it does not make sense to throw... -# #@raises(RuntimeError) -# #def test_pointsymbolizer_missing_image(): -# # p = mapnik.PointSymbolizer(mapnik.PathExpression("../data/images/broken.png")) - -# def test_polygon_symbolizer(): -# p = mapnik.PolygonSymbolizer() -# eq_(p.smooth,0.0) -# eq_(p.comp_op,mapnik.CompositeOp.src_over) -# eq_(p.clip,True) -# eq_(p.fill, mapnik.Color('gray')) -# eq_(p.fill_opacity, 1) - -# p = mapnik.PolygonSymbolizer(mapnik.Color('blue')) - -# eq_(p.fill, mapnik.Color('blue')) -# eq_(p.fill_opacity, 1) - -# def test_building_symbolizer_init(): -# p = mapnik.BuildingSymbolizer() - -# eq_(p.fill, mapnik.Color('gray')) -# eq_(p.fill_opacity, 1) -# eq_(p.height,None) - -# def test_group_symbolizer_init(): -# s = mapnik.GroupSymbolizer() - -# p = mapnik.GroupSymbolizerProperties() - -# l = mapnik.PairLayout() -# l.item_margin = 5.0 -# p.set_layout(l) - -# r = mapnik.GroupRule(mapnik.Expression("[name%1]")) -# r.append(mapnik.PointSymbolizer()) -# p.add_rule(r) -# s.symbolizer_properties = p - -# eq_(s.comp_op,mapnik.CompositeOp.src_over) - -# def test_stroke_init(): -# s = mapnik.Stroke() - -# eq_(s.width, 1) -# eq_(s.opacity, 1) -# eq_(s.color, mapnik.Color('black')) -# eq_(s.line_cap, mapnik.line_cap.BUTT_CAP) -# eq_(s.line_join, mapnik.line_join.MITER_JOIN) -# eq_(s.gamma,1.0) - -# s = mapnik.Stroke(mapnik.Color('blue'), 5.0) -# s.gamma = .5 - -# eq_(s.width, 5) -# eq_(s.opacity, 1) -# eq_(s.color, mapnik.Color('blue')) -# eq_(s.gamma, .5) -# eq_(s.line_cap, mapnik.line_cap.BUTT_CAP) -# eq_(s.line_join, mapnik.line_join.MITER_JOIN) - -# def test_stroke_dash_arrays(): -# s = mapnik.Stroke() -# s.add_dash(1,2) -# s.add_dash(3,4) -# s.add_dash(5,6) - -# eq_(s.get_dashes(), [(1,2),(3,4),(5,6)]) - -# def test_map_init(): -# m = mapnik.Map(256, 256) - -# eq_(m.width, 256) -# eq_(m.height, 256) -# eq_(m.srs, 'epsg:4326') -# eq_(m.base, '') -# eq_(m.maximum_extent, None) -# eq_(m.background_image, None) -# eq_(m.background_image_comp_op, mapnik.CompositeOp.src_over) -# eq_(m.background_image_opacity, 1.0) - -# m = mapnik.Map(256, 256, '+proj=latlong') -# eq_(m.srs, '+proj=latlong') - -# def test_map_style_access(): -# m = mapnik.Map(256, 256) -# sty = mapnik.Style() -# m.append_style("style",sty) -# styles = list(m.styles) -# eq_(len(styles),1) -# eq_(styles[0][0],'style') -# # returns a copy so let's just check it is the right instance -# eq_(isinstance(styles[0][1],mapnik.Style),True) - -# def test_map_maximum_extent_modification(): -# m = mapnik.Map(256, 256) -# eq_(m.maximum_extent, None) -# m.maximum_extent = mapnik.Box2d() -# eq_(m.maximum_extent, mapnik.Box2d()) -# m.maximum_extent = None -# eq_(m.maximum_extent, None) - -# # Map initialization from string -# def test_map_init_from_string(): -# map_string = ''' -# -# -# My Style -# -# shape -# ../../demo/data/boundaries -# -# -# ''' - -# m = mapnik.Map(600, 300) -# eq_(m.base, '') -# try: -# mapnik.load_map_from_string(m, map_string) -# eq_(m.base, './') -# mapnik.load_map_from_string(m, map_string, False, "") # this "" will have no effect -# eq_(m.base, './') - -# tmp_dir = tempfile.gettempdir() -# try: -# mapnik.load_map_from_string(m, map_string, False, tmp_dir) -# except RuntimeError: -# pass # runtime error expected because shapefile path should be wrong and datasource will throw -# eq_(m.base, tmp_dir) # tmp_dir will be set despite the exception because load_map mostly worked -# m.base = 'foo' -# mapnik.load_map_from_string(m, map_string, True, ".") -# eq_(m.base, '.') -# except RuntimeError, e: -# # only test datasources that we have installed -# if not 'Could not create datasource' in str(e): -# raise RuntimeError(e) +import os +import tempfile +import mapnik +import pytest + +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + +def test_debug_symbolizer(setup): + s = mapnik.DebugSymbolizer() + s.mode = mapnik.debug_symbolizer_mode.collision + assert s.mode == mapnik.debug_symbolizer_mode.collision + +def test_raster_symbolizer(): + s = mapnik.RasterSymbolizer() + s.comp_op = mapnik.CompositeOp.src_over + s.scaling = mapnik.scaling_method.NEAR + s.opacity = 1.0 + s.mesh_size = 16 + + assert s.comp_op == mapnik.CompositeOp.src_over # note: mode is deprecated + assert s.scaling == mapnik.scaling_method.NEAR + assert s.opacity == 1.0 + assert s.colorizer == None + assert s.mesh_size == 16 + assert s.premultiplied == None + s.premultiplied = True + assert s.premultiplied == True + +def test_line_pattern(): + s = mapnik.LinePatternSymbolizer() + s.file = mapnik.PathExpression('../data/images/dummy.png') + assert str(s.file) == '../data/images/dummy.png' + +def test_map_init(): + m = mapnik.Map(256, 256) + assert m.width == 256 + assert m.height == 256 + assert m.srs == 'epsg:4326' + assert m.base == '' + assert m.maximum_extent == None + assert m.background_image == None + assert m.background_image_comp_op == mapnik.CompositeOp.src_over + assert m.background_image_opacity == 1.0 + m = mapnik.Map(256, 256, '+proj=latlong') + assert m.srs == '+proj=latlong' + +def test_map_style_access(): + m = mapnik.Map(256, 256) + sty = mapnik.Style() + m.append_style("style",sty) + styles = list(m.styles) + assert len(styles) == 1 + assert styles[0][0] == 'style' + # returns a copy so let's just check it is the right instance + assert isinstance(styles[0][1],mapnik.Style) + +def test_map_maximum_extent_modification(): + m = mapnik.Map(256, 256) + assert m.maximum_extent == None + m.maximum_extent = mapnik.Box2d() + assert m.maximum_extent == mapnik.Box2d() + m.maximum_extent = None + assert m.maximum_extent == None + +# Map initialization from string +def test_map_init_from_string(): + map_string = ''' + + + My Style + + shape + ../../demo/data/boundaries + + + ''' + + m = mapnik.Map(600, 300) + assert m.base == '' + try: + mapnik.load_map_from_string(m, map_string) + assert m.base == './' + mapnik.load_map_from_string(m, map_string, False, "") # this "" will have no effect + assert m.base == './' + + tmp_dir = tempfile.gettempdir() + try: + mapnik.load_map_from_string(m, map_string, False, tmp_dir) + except RuntimeError: + pass # runtime error expected because shapefile path should be wrong and datasource will throw + assert m.base == tmp_dir # tmp_dir will be set despite the exception because load_map mostly worked + m.remove_all() + m.base = 'foo' + mapnik.load_map_from_string(m, map_string, True, ".") + assert m.base == '.' + except RuntimeError as e: + # only test datasources that we have installed + if not 'Could not create datasource' in str(e): + raise RuntimeError(e) # # Color initialization -# @raises(Exception) # Boost.Python.ArgumentError -# def test_color_init_errors(): -# c = mapnik.Color() +def test_color_init_errors(): + with pytest.raises(Exception): # Boost.Python.ArgumentError + c = mapnik.Color() -# @raises(RuntimeError) -# def test_color_init_errors(): -# c = mapnik.Color('foo') # mapnik config +def test_color_init_errors(): + with pytest.raises(RuntimeError): + c = mapnik.Color('foo') # mapnik config -# def test_color_init(): -# c = mapnik.Color('blue') +def test_color_init(): + c = mapnik.Color('blue') + assert c.a == 255 + assert c.r == 0 + assert c.g == 0 + assert c.b == 255 -# eq_(c.a, 255) -# eq_(c.r, 0) -# eq_(c.g, 0) -# eq_(c.b, 255) + assert c.to_hex_string() == '#0000ff' -# eq_(c.to_hex_string(), '#0000ff') + c = mapnik.Color('#f2eff9') -# c = mapnik.Color('#f2eff9') + assert c.a == 255 + assert c.r == 242 + assert c.g == 239 + assert c.b == 249 -# eq_(c.a, 255) -# eq_(c.r, 242) -# eq_(c.g, 239) -# eq_(c.b, 249) + assert c.to_hex_string() == '#f2eff9' -# eq_(c.to_hex_string(), '#f2eff9') + c = mapnik.Color('rgb(50%,50%,50%)') -# c = mapnik.Color('rgb(50%,50%,50%)') + assert c.a == 255 + assert c.r == 128 + assert c.g == 128 + assert c.b == 128 -# eq_(c.a, 255) -# eq_(c.r, 128) -# eq_(c.g, 128) -# eq_(c.b, 128) + assert c.to_hex_string() == '#808080' -# eq_(c.to_hex_string(), '#808080') + c = mapnik.Color(0, 64, 128) -# c = mapnik.Color(0, 64, 128) + assert c.a == 255 + assert c.r == 0 + assert c.g == 64 + assert c.b == 128 -# eq_(c.a, 255) -# eq_(c.r, 0) -# eq_(c.g, 64) -# eq_(c.b, 128) + assert c.to_hex_string() == '#004080' -# eq_(c.to_hex_string(), '#004080') + c = mapnik.Color(0, 64, 128, 192) -# c = mapnik.Color(0, 64, 128, 192) + assert c.a == 192 + assert c.r == 0 + assert c.g == 64 + assert c.b == 128 -# eq_(c.a, 192) -# eq_(c.r, 0) -# eq_(c.g, 64) -# eq_(c.b, 128) + assert c.to_hex_string() == '#004080c0' -# eq_(c.to_hex_string(), '#004080c0') +def test_color_equality(): -# def test_color_equality(): + c1 = mapnik.Color('blue') + c2 = mapnik.Color(0,0,255) + c3 = mapnik.Color('black') -# c1 = mapnik.Color('blue') -# c2 = mapnik.Color(0,0,255) -# c3 = mapnik.Color('black') + c3.r = 0 + c3.g = 0 + c3.b = 255 + c3.a = 255 -# c3.r = 0 -# c3.g = 0 -# c3.b = 255 -# c3.a = 255 + assert c1 == c2 + assert c1 == c3 -# eq_(c1, c2) -# eq_(c1, c3) + c1 = mapnik.Color(0, 64, 128) + c2 = mapnik.Color(0, 64, 128) + c3 = mapnik.Color(0, 0, 0) -# c1 = mapnik.Color(0, 64, 128) -# c2 = mapnik.Color(0, 64, 128) -# c3 = mapnik.Color(0, 0, 0) + c3.r = 0 + c3.g = 64 + c3.b = 128 -# c3.r = 0 -# c3.g = 64 -# c3.b = 128 + assert c1 == c2 + assert c1 == c3 -# eq_(c1, c2) -# eq_(c1, c3) + c1 = mapnik.Color(0, 64, 128, 192) + c2 = mapnik.Color(0, 64, 128, 192) + c3 = mapnik.Color(0, 0, 0, 255) -# c1 = mapnik.Color(0, 64, 128, 192) -# c2 = mapnik.Color(0, 64, 128, 192) -# c3 = mapnik.Color(0, 0, 0, 255) + c3.r = 0 + c3.g = 64 + c3.b = 128 + c3.a = 192 -# c3.r = 0 -# c3.g = 64 -# c3.b = 128 -# c3.a = 192 + assert c1 == c2 + assert c1 == c3 -# eq_(c1, c2) -# eq_(c1, c3) + c1 = mapnik.Color('rgb(50%,50%,50%)') + c2 = mapnik.Color(128, 128, 128, 255) + c3 = mapnik.Color('#808080') + c4 = mapnik.Color('gray') -# c1 = mapnik.Color('rgb(50%,50%,50%)') -# c2 = mapnik.Color(128, 128, 128, 255) -# c3 = mapnik.Color('#808080') -# c4 = mapnik.Color('gray') + assert c1 == c2 + assert c1 == c3 + assert c1 == c4 -# eq_(c1, c2) -# eq_(c1, c3) -# eq_(c1, c4) + c1 = mapnik.Color('hsl(0, 100%, 50%)') # red + c2 = mapnik.Color('hsl(120, 100%, 50%)') # lime + c3 = mapnik.Color('hsla(240, 100%, 50%, 0.5)') # semi-transparent solid blue -# c1 = mapnik.Color('hsl(0, 100%, 50%)') # red -# c2 = mapnik.Color('hsl(120, 100%, 50%)') # lime -# c3 = mapnik.Color('hsla(240, 100%, 50%, 0.5)') # semi-transparent solid -# blue + assert c1 == mapnik.Color('red') + assert c2 == mapnik.Color('lime') + assert c3, mapnik.Color(0,0,255 == 128) -# eq_(c1, mapnik.Color('red')) -# eq_(c2, mapnik.Color('lime')) -# eq_(c3, mapnik.Color(0,0,255,128)) +def test_rule_init(): + min_scale = 5 + max_scale = 10 -# def test_rule_init(): -# min_scale = 5 -# max_scale = 10 + r = mapnik.Rule() -# r = mapnik.Rule() + assert r.name == '' + assert r.min_scale == 0 + assert r.max_scale == float('inf') + assert r.has_else() == False + assert r.has_also() == False -# eq_(r.name, '') -# eq_(r.min_scale, 0) -# eq_(r.max_scale, float('inf')) -# eq_(r.has_else(), False) -# eq_(r.has_also(), False) + r = mapnik.Rule() -# r = mapnik.Rule() + r.set_else(True) + assert r.has_else() == True + assert r.has_also() == False -# r.set_else(True) -# eq_(r.has_else(), True) -# eq_(r.has_also(), False) + r = mapnik.Rule() -# r = mapnik.Rule() + r.set_also(True) + assert r.has_else() == False + assert r.has_also() == True -# r.set_also(True) -# eq_(r.has_else(), False) -# eq_(r.has_also(), True) + r = mapnik.Rule("Name") -# r = mapnik.Rule("Name") + assert r.name == 'Name' + assert r.min_scale == 0 + assert r.max_scale == float('inf') + assert r.has_else() == False + assert r.has_also() == False -# eq_(r.name, 'Name') -# eq_(r.min_scale, 0) -# eq_(r.max_scale, float('inf')) -# eq_(r.has_else(), False) -# eq_(r.has_also(), False) + r = mapnik.Rule("Name") -# r = mapnik.Rule("Name") + assert r.name == 'Name' + assert r.min_scale == 0 + assert r.max_scale == float('inf') + assert r.has_else() == False + assert r.has_also() == False -# eq_(r.name, 'Name') -# eq_(r.min_scale, 0) -# eq_(r.max_scale, float('inf')) -# eq_(r.has_else(), False) -# eq_(r.has_also(), False) + r = mapnik.Rule("Name", min_scale) -# r = mapnik.Rule("Name", min_scale) + assert r.name == 'Name' + assert r.min_scale == min_scale + assert r.max_scale == float('inf') + assert r.has_else() == False + assert r.has_also() == False -# eq_(r.name, 'Name') -# eq_(r.min_scale, min_scale) -# eq_(r.max_scale, float('inf')) -# eq_(r.has_else(), False) -# eq_(r.has_also(), False) + r = mapnik.Rule("Name", min_scale, max_scale) -# r = mapnik.Rule("Name", min_scale, max_scale) - -# eq_(r.name, 'Name') -# eq_(r.min_scale, min_scale) -# eq_(r.max_scale, max_scale) -# eq_(r.has_else(), False) -# eq_(r.has_also(), False) - -# if __name__ == "__main__": -# setup() -# run_all(eval(x) for x in dir() if x.startswith("test_")) + assert r.name == 'Name' + assert r.min_scale == min_scale + assert r.max_scale == max_scale + assert r.has_else() == False + assert r.has_also() == False diff --git a/test/python_tests/ogr_and_shape_geometries_test.py b/test/python_tests/ogr_and_shape_geometries_test.py index 49644e9e8..20cb509ff 100644 --- a/test/python_tests/ogr_and_shape_geometries_test.py +++ b/test/python_tests/ogr_and_shape_geometries_test.py @@ -1,4 +1,14 @@ +import os +import pytest import mapnik +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield try: import itertools.izip as zip @@ -30,6 +40,6 @@ def ensure_geometries_are_interpreted_equivalently(filename): assert feat1.geometry.to_wkb(mapnik.wkbByteOrder.NDR) == feat2.geometry.to_wkb(mapnik.wkbByteOrder.NDR) assert feat1.geometry.to_wkb(mapnik.wkbByteOrder.XDR) == feat2.geometry.to_wkb(mapnik.wkbByteOrder.XDR) - def test_simple_polys(): + def test_simple_polys(setup): ensure_geometries_are_interpreted_equivalently( - './test/data/shp/wkt_poly.shp') + '../data/shp/wkt_poly.shp') diff --git a/test/python_tests/ogr_test.py b/test/python_tests/ogr_test.py index b35f80f7e..a4ff7f2ef 100644 --- a/test/python_tests/ogr_test.py +++ b/test/python_tests/ogr_test.py @@ -1,3 +1,4 @@ +import os import mapnik import pytest @@ -6,11 +7,20 @@ except ImportError: import simplejson as json +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + if 'ogr' in mapnik.DatasourceCache.plugin_names(): # Shapefile initialization - def test_shapefile_init(): - ds = mapnik.Ogr(file='./test/data/shp/boundaries.shp', layer_by_index=0) + def test_shapefile_init(setup): + ds = mapnik.Ogr(file='../data/shp/boundaries.shp', layer_by_index=0) e = ds.envelope() assert e.minx == pytest.approx(-11121.6896651, abs=1e-7) assert e.miny == pytest.approx(-724724.216526, abs=1e-6) @@ -22,7 +32,7 @@ def test_shapefile_init(): # Shapefile properties def test_shapefile_properties(): - ds = mapnik.Ogr(file='./test/data/shp/boundaries.shp', layer_by_index=0) + ds = mapnik.Ogr(file='../data/shp/boundaries.shp', layer_by_index=0) f = list(ds.features_at_point(ds.envelope().center(), 0.001))[0] assert ds.geometry_type() == mapnik.DataGeometryType.Polygon @@ -39,7 +49,7 @@ def test_shapefile_properties(): def test_that_nonexistant_query_field_throws(**kwargs): with pytest.raises(RuntimeError): - ds = mapnik.Ogr(file='./test/data/shp/world_merc.shp', layer_by_index=0) + ds = mapnik.Ogr(file='../data/shp/world_merc.shp', layer_by_index=0) assert len(ds.fields()) == 11 assert ds.fields() == ['FIPS', 'ISO2', 'ISO3', 'UN', 'NAME', 'AREA', 'POP2005', 'REGION', 'SUBREGION', 'LON', 'LAT'] @@ -53,14 +63,14 @@ def test_that_nonexistant_query_field_throws(**kwargs): # disabled because OGR prints an annoying error: ERROR 1: Invalid Point object. Missing 'coordinates' member. # def test_handling_of_null_features(): - # ds = mapnik.Ogr(file='./test/data/json/null_feature.geojson',layer_by_index=0) + # ds = mapnik.Ogr(file='../data/json/null_feature.geojson',layer_by_index=0) # fs = ds.all_features() # assert len(list(fs)) == 1 # OGR plugin extent parameter def test_ogr_extent_parameter(): ds = mapnik.Ogr( - file='./test/data/shp/world_merc.shp', + file='../data/shp/world_merc.shp', layer_by_index=0, extent='-1,-1,1,1') e = ds.envelope() @@ -73,7 +83,7 @@ def test_ogr_extent_parameter(): assert '+proj=merc' in meta['proj4'] def test_ogr_reading_gpx_waypoint(): - ds = mapnik.Ogr(file='./test/data/gpx/empty.gpx', layer='waypoints') + ds = mapnik.Ogr(file='../data/gpx/empty.gpx', layer='waypoints') e = ds.envelope() assert e.minx == -122 assert e.miny == 48 @@ -88,7 +98,7 @@ def test_ogr_empty_data_should_not_throw(): mapnik.logger.set_severity(getattr(mapnik.severity_type, "None")) # use logger to silence expected warnings for layer in ['routes', 'tracks', 'route_points', 'track_points']: - ds = mapnik.Ogr(file='./test/data/gpx/empty.gpx', layer=layer) + ds = mapnik.Ogr(file='../data/gpx/empty.gpx', layer=layer) e = ds.envelope() assert e.minx == 0 assert e.miny == 0 @@ -102,12 +112,12 @@ def test_ogr_empty_data_should_not_throw(): # disabled because OGR prints an annoying error: ERROR 1: Invalid Point object. Missing 'coordinates' member. def test_handling_of_null_features(): assert True - ds = mapnik.Ogr(file='./test/data/json/null_feature.geojson',layer_by_index=0) + ds = mapnik.Ogr(file='../data/json/null_feature.geojson',layer_by_index=0) fs = ds.all_features() assert len(list(fs)) == 1 def test_geometry_type(): - ds = mapnik.Ogr(file='./test/data/csv/wkt.csv', layer_by_index=0) + ds = mapnik.Ogr(file='../data/csv/wkt.csv', layer_by_index=0) e = ds.envelope() assert e.minx == pytest.approx(1.0, abs=1e-1) assert e.miny == pytest.approx(1.0, abs=1e-1) diff --git a/test/python_tests/palette_test.py b/test/python_tests/palette_test.py index 849a6c3f1..23a934e63 100644 --- a/test/python_tests/palette_test.py +++ b/test/python_tests/palette_test.py @@ -1,5 +1,14 @@ import sys, os import mapnik +import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield expected_64 = '[Palette 64 colors #494746 #c37631 #89827c #d1955c #7397b9 #fc9237 #a09f9c #fbc147 #9bb3ce #b7c9a1 #b5d29c #c4b9aa #cdc4a5 #d5c8a3 #c1d7aa #ccc4b6 #dbd19c #b2c4d5 #eae487 #c9c8c6 #e4db99 #c9dcb5 #dfd3ac #cbd2c2 #d6cdbc #dbd2b6 #c0ceda #ece597 #f7ef86 #d7d3c3 #dfcbc3 #d1d0cd #d1e2bf #d3dec1 #dbd3c4 #e6d8b6 #f4ef91 #d3d3cf #cad5de #ded7c9 #dfdbce #fcf993 #ffff8a #dbd9d7 #dbe7cd #d4dce2 #e4ded3 #ebe3c9 #e0e2e2 #f4edc3 #fdfcae #e9e5dc #f4edda #eeebe4 #fefdc5 #e7edf2 #edf4e5 #f2efe9 #f6ede7 #fefedd #f6f4f0 #f1f5f8 #fbfaf8 #ffffff]' @@ -8,11 +17,11 @@ expected_rgb = '[Palette 2 colors #ff00ff #ffffff]' -def test_reading_palettes(): - with open('./test/data/palettes/palette64.act', 'rb') as act: +def test_reading_palettes(setup): + with open('../data/palettes/palette64.act', 'rb') as act: palette = mapnik.Palette(act.read(), 'act') assert palette.to_string() == expected_64 - with open('./test/data/palettes/palette256.act', 'rb') as act: + with open('../data/palettes/palette256.act', 'rb') as act: palette = mapnik.Palette(act.read(), 'act') assert palette.to_string() == expected_256 palette = mapnik.Palette(b'\xff\x00\xff\xff\xff\xff', 'rgb') @@ -22,15 +31,15 @@ def test_reading_palettes(): def test_render_with_palette(): m = mapnik.Map(600, 400) - mapnik.load_map(m, './test/data/good_maps/agg_poly_gamma_map.xml') + mapnik.load_map(m, '../data/good_maps/agg_poly_gamma_map.xml') m.zoom_all() im = mapnik.Image(m.width, m.height) mapnik.render(m, im) - with open('./test/data/palettes/palette256.act', 'rb') as act: + with open('../data/palettes/palette256.act', 'rb') as act: palette = mapnik.Palette(act.read(), 'act') # test saving directly to filesystem im.save('/tmp/mapnik-palette-test.png', 'png', palette) - expected = './test/python_tests/images/support/mapnik-palette-test.png' + expected = 'images/support/mapnik-palette-test.png' if os.environ.get('UPDATE'): im.save(expected, "png", palette) diff --git a/test/python_tests/pdf_printing_test.py b/test/python_tests/pdf_printing_test.py index 83efcc880..3240231c0 100644 --- a/test/python_tests/pdf_printing_test.py +++ b/test/python_tests/pdf_printing_test.py @@ -1,5 +1,14 @@ import mapnik import os +import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield def make_map_from_xml(source_xml): m = mapnik.Map(100, 100) @@ -21,15 +30,15 @@ def make_pdf(m, output_pdf, esri_wkt): if mapnik.has_pycairo(): import mapnik.printing - def test_pdf_printing(): - source_xml = './test/data/good_maps/marker-text-line.xml'.encode('utf-8') + def test_pdf_printing(setup): + source_xml = '../data/good_maps/marker-text-line.xml'.encode('utf-8') m = make_map_from_xml(source_xml) actual_pdf = "/tmp/pdf-printing-actual.pdf" esri_wkt = 'GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137,298.257223563]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]]' make_pdf(m, actual_pdf, esri_wkt) - expected_pdf = './test/python_tests/images/pycairo/pdf-printing-expected.pdf' + expected_pdf = 'images/pycairo/pdf-printing-expected.pdf' diff = abs(os.stat(expected_pdf).st_size - os.stat(actual_pdf).st_size) msg = 'diff in size (%s) between actual (%s) and expected(%s)' % (diff, actual_pdf, 'tests/python_tests/' + expected_pdf) diff --git a/test/python_tests/pgraster_test.py b/test/python_tests/pgraster_test.py index 2bb438305..e7bb66139 100644 --- a/test/python_tests/pgraster_test.py +++ b/test/python_tests/pgraster_test.py @@ -1,5 +1,3 @@ -#!/usr/bin/env python - import atexit import os import re @@ -7,12 +5,9 @@ import time from binascii import hexlify from subprocess import PIPE, Popen - -from nose.tools import assert_almost_equal, eq_ - import mapnik - -from .utilities import execution_path, run_all, side_by_side_image +import pytest +from .utilities import execution_path, side_by_side_image MAPNIK_TEST_DBNAME = 'mapnik-tmp-pgraster-test-db' POSTGIS_TEMPLATE_DBNAME = 'template_postgis' @@ -23,7 +18,7 @@ def log(msg): if DEBUG_OUTPUT: print(msg) - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() @@ -825,15 +820,8 @@ def test_rgba_8bui_subquery(): atexit.register(postgis_takedown) - def enabled(tname): enabled = len(sys.argv) < 2 or tname in sys.argv if not enabled: print("Skipping " + tname + " as not explicitly enabled") return enabled - -if __name__ == "__main__": - setup() - fail = run_all(eval(x) - for x in dir() if x.startswith("test_") and enabled(x)) - exit(fail) diff --git a/test/python_tests/png_encoding_test.py b/test/python_tests/png_encoding_test.py index 92858b1a4..1b52983a9 100644 --- a/test/python_tests/png_encoding_test.py +++ b/test/python_tests/png_encoding_test.py @@ -8,6 +8,7 @@ def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield if mapnik.has_png(): tmp_dir = '/tmp/mapnik-png/' diff --git a/test/python_tests/pngsuite_test.py b/test/python_tests/pngsuite_test.py index 2f773578d..8c91e27ce 100644 --- a/test/python_tests/pngsuite_test.py +++ b/test/python_tests/pngsuite_test.py @@ -10,7 +10,7 @@ def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) - + yield def assert_broken_file(fname): with pytest.raises(RuntimeError): diff --git a/test/python_tests/projection_test.py b/test/python_tests/projection_test.py index 93e501e3d..1a6df09dd 100644 --- a/test/python_tests/projection_test.py +++ b/test/python_tests/projection_test.py @@ -1,25 +1,16 @@ -#!/usr/bin/env python import math import sys - -from nose.tools import assert_almost_equal, eq_ - import mapnik +import pytest -from .utilities import assert_box2d_almost_equal, run_all - -PYTHON3 = sys.version_info[0] == 3 -if PYTHON3: - xrange = range +from .utilities import assert_box2d_almost_equal # Tests that exercise map projections. - def test_normalizing_definition(): p = mapnik.Projection('epsg:4326') expanded = p.expanded() - eq_('+proj=longlat' in expanded, True) - + assert '+proj=longlat' in expanded # Trac Ticket #128 def test_wgs84_inverse_forward(): @@ -31,29 +22,29 @@ def test_wgs84_inverse_forward(): # It appears that the y component changes very slightly, is this OK? # so we test for 'almost equal float values' - assert_almost_equal(p.inverse(c).y, c.y) - assert_almost_equal(p.inverse(c).x, c.x) + assert p.inverse(c).y == pytest.approx(c.y) + assert p.inverse(c).x == pytest.approx(c.x) - assert_almost_equal(p.forward(c).y, c.y) - assert_almost_equal(p.forward(c).x, c.x) + assert p.forward(c).y == pytest.approx(c.y) + assert p.forward(c).x == pytest.approx(c.x) - assert_almost_equal(p.inverse(e).center().y, e.center().y) - assert_almost_equal(p.inverse(e).center().x, e.center().x) + assert p.inverse(e).center().y == pytest.approx(e.center().y) + assert p.inverse(e).center().x == pytest.approx(e.center().x) - assert_almost_equal(p.forward(e).center().y, e.center().y) - assert_almost_equal(p.forward(e).center().x, e.center().x) + assert p.forward(e).center().y == pytest.approx(e.center().y) + assert p.forward(e).center().x == pytest.approx(e.center().x) - assert_almost_equal(c.inverse(p).y, c.y) - assert_almost_equal(c.inverse(p).x, c.x) + assert c.inverse(p).y == pytest.approx(c.y) + assert c.inverse(p).x == pytest.approx(c.x) - assert_almost_equal(c.forward(p).y, c.y) - assert_almost_equal(c.forward(p).x, c.x) + assert c.forward(p).y == pytest.approx(c.y) + assert c.forward(p).x == pytest.approx(c.x) - assert_almost_equal(e.inverse(p).center().y, e.center().y) - assert_almost_equal(e.inverse(p).center().x, e.center().x) + assert e.inverse(p).center().y == pytest.approx(e.center().y) + assert e.inverse(p).center().x == pytest.approx(e.center().x) - assert_almost_equal(e.forward(p).center().y, e.center().y) - assert_almost_equal(e.forward(p).center().x, e.center().x) + assert e.forward(p).center().y == pytest.approx(e.center().y) + assert e.forward(p).center().x == pytest.approx(e.center().x) def wgs2merc(lon, lat): @@ -99,33 +90,33 @@ def test_proj_transform_between_init_and_literal(): dest = mapnik.Projection(merc) tr2 = mapnik.ProjTransform(src, dest) tr2b = mapnik.ProjTransform(dest, src) - for x in xrange(-180, 180, 10): - for y in xrange(-60, 60, 10): + for x in range(-180, 180, 10): + for y in range(-60, 60, 10): coord = mapnik.Coord(x, y) merc_coord1 = tr1.forward(coord) merc_coord2 = tr1b.backward(coord) merc_coord3 = tr2.forward(coord) merc_coord4 = tr2b.backward(coord) - eq_(math.fabs(merc_coord1.x - merc_coord1.x) < 1, True) - eq_(math.fabs(merc_coord1.x - merc_coord2.x) < 1, True) - eq_(math.fabs(merc_coord1.x - merc_coord3.x) < 1, True) - eq_(math.fabs(merc_coord1.x - merc_coord4.x) < 1, True) - eq_(math.fabs(merc_coord1.y - merc_coord1.y) < 1, True) - eq_(math.fabs(merc_coord1.y - merc_coord2.y) < 1, True) - eq_(math.fabs(merc_coord1.y - merc_coord3.y) < 1, True) - eq_(math.fabs(merc_coord1.y - merc_coord4.y) < 1, True) + assert math.fabs(merc_coord1.x - merc_coord1.x) < 1 + assert math.fabs(merc_coord1.x - merc_coord2.x) < 1 + assert math.fabs(merc_coord1.x - merc_coord3.x) < 1 + assert math.fabs(merc_coord1.x - merc_coord4.x) < 1 + assert math.fabs(merc_coord1.y - merc_coord1.y) < 1 + assert math.fabs(merc_coord1.y - merc_coord2.y) < 1 + assert math.fabs(merc_coord1.y - merc_coord3.y) < 1 + assert math.fabs(merc_coord1.y - merc_coord4.y) < 1 lon_lat_coord1 = tr1.backward(merc_coord1) lon_lat_coord2 = tr1b.forward(merc_coord2) lon_lat_coord3 = tr2.backward(merc_coord3) lon_lat_coord4 = tr2b.forward(merc_coord4) - eq_(math.fabs(coord.x - lon_lat_coord1.x) < 1, True) - eq_(math.fabs(coord.x - lon_lat_coord2.x) < 1, True) - eq_(math.fabs(coord.x - lon_lat_coord3.x) < 1, True) - eq_(math.fabs(coord.x - lon_lat_coord4.x) < 1, True) - eq_(math.fabs(coord.y - lon_lat_coord1.y) < 1, True) - eq_(math.fabs(coord.y - lon_lat_coord2.y) < 1, True) - eq_(math.fabs(coord.y - lon_lat_coord3.y) < 1, True) - eq_(math.fabs(coord.y - lon_lat_coord4.y) < 1, True) + assert math.fabs(coord.x - lon_lat_coord1.x) < 1 + assert math.fabs(coord.x - lon_lat_coord2.x) < 1 + assert math.fabs(coord.x - lon_lat_coord3.x) < 1 + assert math.fabs(coord.x - lon_lat_coord4.x) < 1 + assert math.fabs(coord.y - lon_lat_coord1.y) < 1 + assert math.fabs(coord.y - lon_lat_coord2.y) < 1 + assert math.fabs(coord.y - lon_lat_coord3.y) < 1 + assert math.fabs(coord.y - lon_lat_coord4.y) < 1 # Github Issue #2648 @@ -162,7 +153,3 @@ def test_proj_antimeridian_bbox(): ext = mapnik.Box2d(274000, 3087000, 276000, 7173000) rev_ext = prj_trans_rev.backward(ext, PROJ_ENVELOPE_POINTS) assert_box2d_almost_equal(rev_ext, normal) - - -if __name__ == "__main__": - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) diff --git a/test/python_tests/query_test.py b/test/python_tests/query_test.py index d4298b665..8a0d58903 100644 --- a/test/python_tests/query_test.py +++ b/test/python_tests/query_test.py @@ -1,44 +1,33 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - import os - -from nose.tools import assert_almost_equal, eq_, raises - import mapnik +import pytest +from .utilities import execution_path -from .utilities import execution_path, run_all - - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield - -def test_query_init(): +def test_query_init(setup): bbox = (-180, -90, 180, 90) query = mapnik.Query(mapnik.Box2d(*bbox)) r = query.resolution - assert_almost_equal(r[0], 1.0, places=7) - assert_almost_equal(r[1], 1.0, places=7) + assert r[0] == pytest.approx(1.0, abs=1e-7) + assert r[1] == pytest.approx(1.0, abs=1e-7) # https://github.com/mapnik/mapnik/issues/1762 - eq_(query.property_names, []) + assert query.property_names == [] query.add_property_name('migurski') - eq_(query.property_names, ['migurski']) + assert query.property_names == ['migurski'] # Converting *from* tuples *to* resolutions is not yet supported - -@raises(TypeError) def test_query_resolution(): - bbox = (-180, -90, 180, 90) - init_res = (4.5, 6.7) - query = mapnik.Query(mapnik.Box2d(*bbox), init_res) - r = query.resolution - assert_almost_equal(r[0], init_res[0], places=7) - assert_almost_equal(r[1], init_res[1], places=7) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + with pytest.raises(TypeError): + bbox = (-180, -90, 180, 90) + init_res = (4.5, 6.7) + query = mapnik.Query(mapnik.Box2d(*bbox), init_res) + r = query.resolution + assert r[0] == pytest.approx(init_res[0], abs=1e-7) + assert r[1] == pytest.approx(init_res[1], abs=1e-7) diff --git a/test/python_tests/query_tolerance_test.py b/test/python_tests/query_tolerance_test.py index b60611334..da2a1cf60 100644 --- a/test/python_tests/query_tolerance_test.py +++ b/test/python_tests/query_tolerance_test.py @@ -1,21 +1,17 @@ -#!/usr/bin/env python - import os - -from nose.tools import eq_ - import mapnik +import pytest +from .utilities import execution_path -from .utilities import execution_path, run_all - - +@pytest.fixture def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield if 'shape' in mapnik.DatasourceCache.plugin_names(): - def test_query_tolerance(): + def test_query_tolerance(setup): srs = 'epsg:4326' lyr = mapnik.Layer('test') ds = mapnik.Shapefile(file='../data/shp/arrows.shp') @@ -29,20 +25,16 @@ def test_query_tolerance(): _map_env = _map.envelope() tol = (_map_env.maxx - _map_env.minx) / _width * 3 # 0.046875 for arrows.shp and zoom_all - eq_(tol, 0.046875) + assert tol == 0.046875 # check point really exists x, y = 2.0, 4.0 features = _map.query_point(0, x, y) - eq_(len(list(features)), 1) + assert len(list(features)) == 1 # check inside tolerance limit x = 2.0 + tol * 0.9 features = _map.query_point(0, x, y) - eq_(len(list(features)), 1) + assert len(list(features)) == 1 # check outside tolerance limit x = 2.0 + tol * 1.1 features = _map.query_point(0, x, y) - eq_(len(list(features)), 0) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert len(list(features)) == 0 diff --git a/test/python_tests/raster_colorizer_test.py b/test/python_tests/raster_colorizer_test.py index 8ae69822c..e9995a5fe 100644 --- a/test/python_tests/raster_colorizer_test.py +++ b/test/python_tests/raster_colorizer_test.py @@ -1,25 +1,19 @@ -# coding=utf8 import os import sys - -from nose.tools import eq_ - +import pytest import mapnik -from .utilities import execution_path, run_all - -PYTHON3 = sys.version_info[0] == 3 - +from .utilities import execution_path +@pytest.fixture def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield # test discrete colorizer mode - - -def test_get_color_discrete(): +def test_get_color_discrete(setup): # setup colorizer = mapnik.RasterColorizer() colorizer.default_color = mapnik.Color(0, 0, 0, 0) @@ -29,16 +23,16 @@ def test_get_color_discrete(): colorizer.add_stop(20, mapnik.Color(200, 200, 200, 200)) # should be default colour - eq_(colorizer.get_color(-50), mapnik.Color(0, 0, 0, 0)) - eq_(colorizer.get_color(0), mapnik.Color(0, 0, 0, 0)) + assert colorizer.get_color(-50) == mapnik.Color(0, 0, 0, 0) + assert colorizer.get_color(0) == mapnik.Color(0, 0, 0, 0) # now in stop 1 - eq_(colorizer.get_color(10), mapnik.Color(100, 100, 100, 100)) - eq_(colorizer.get_color(19), mapnik.Color(100, 100, 100, 100)) + assert colorizer.get_color(10) == mapnik.Color(100, 100, 100, 100) + assert colorizer.get_color(19) == mapnik.Color(100, 100, 100, 100) # now in stop 2 - eq_(colorizer.get_color(20), mapnik.Color(200, 200, 200, 200)) - eq_(colorizer.get_color(1000), mapnik.Color(200, 200, 200, 200)) + assert colorizer.get_color(20) == mapnik.Color(200, 200, 200, 200) + assert colorizer.get_color(1000) == mapnik.Color(200, 200, 200, 200) # test exact colorizer mode @@ -53,15 +47,15 @@ def test_get_color_exact(): colorizer.add_stop(20, mapnik.Color(200, 200, 200, 200)) # should be default colour - eq_(colorizer.get_color(-50), mapnik.Color(0, 0, 0, 0)) - eq_(colorizer.get_color(11), mapnik.Color(0, 0, 0, 0)) - eq_(colorizer.get_color(20.001), mapnik.Color(0, 0, 0, 0)) + assert colorizer.get_color(-50) == mapnik.Color(0, 0, 0, 0) + assert colorizer.get_color(11) == mapnik.Color(0, 0, 0, 0) + assert colorizer.get_color(20.001) == mapnik.Color(0, 0, 0, 0) # should be stop 1 - eq_(colorizer.get_color(10), mapnik.Color(100, 100, 100, 100)) + assert colorizer.get_color(10) == mapnik.Color(100, 100, 100, 100) # should be stop 2 - eq_(colorizer.get_color(20), mapnik.Color(200, 200, 200, 200)) + assert colorizer.get_color(20) == mapnik.Color(200, 200, 200, 200) # test linear colorizer mode @@ -76,20 +70,20 @@ def test_get_color_linear(): colorizer.add_stop(20, mapnik.Color(200, 200, 200, 200)) # should be default colour - eq_(colorizer.get_color(-50), mapnik.Color(0, 0, 0, 0)) - eq_(colorizer.get_color(9.9), mapnik.Color(0, 0, 0, 0)) + assert colorizer.get_color(-50) == mapnik.Color(0, 0, 0, 0) + assert colorizer.get_color(9.9) == mapnik.Color(0, 0, 0, 0) # should be stop 1 - eq_(colorizer.get_color(10), mapnik.Color(100, 100, 100, 100)) + assert colorizer.get_color(10) == mapnik.Color(100, 100, 100, 100) # should be stop 2 - eq_(colorizer.get_color(20), mapnik.Color(200, 200, 200, 200)) + assert colorizer.get_color(20) == mapnik.Color(200, 200, 200, 200) # half way between stops 1 and 2 - eq_(colorizer.get_color(15), mapnik.Color(150, 150, 150, 150)) + assert colorizer.get_color(15) == mapnik.Color(150, 150, 150, 150) # after stop 2 - eq_(colorizer.get_color(100), mapnik.Color(200, 200, 200, 200)) + assert colorizer.get_color(100) == mapnik.Color(200, 200, 200, 200) def test_stop_label(): @@ -97,11 +91,5 @@ def test_stop_label(): 1, mapnik.COLORIZER_LINEAR, mapnik.Color('red')) assert not stop.label label = u"32º C" - if not PYTHON3: - label = label.encode('utf8') stop.label = label assert stop.label == label, stop.label - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) diff --git a/test/python_tests/raster_symbolizer_test.py b/test/python_tests/raster_symbolizer_test.py index 0a0beb45f..9dc6610ed 100644 --- a/test/python_tests/raster_symbolizer_test.py +++ b/test/python_tests/raster_symbolizer_test.py @@ -1,21 +1,16 @@ -#!/usr/bin/env python - import os - -from nose.tools import eq_ - import mapnik +import pytest +from .utilities import execution_path, get_unique_colors -from .utilities import execution_path, get_unique_colors, run_all - - +@pytest.fixture def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield - -def test_dataraster_coloring(): +def test_dataraster_coloring(setup): srs = 'epsg:32630' lyr = mapnik.Layer('dataraster') if 'gdal' in mapnik.DatasourceCache.plugin_names(): @@ -65,10 +60,8 @@ def test_dataraster_coloring(): im.save(expected_file, 'png32') actual = mapnik.Image.open(actual_file) expected = mapnik.Image.open(expected_file) - eq_(actual.tostring('png32'), - expected.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual_file, - expected_file)) + assert actual.tostring('png32') == expected.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual_file, + expected_file) def test_dataraster_query_point(): @@ -153,7 +146,7 @@ def test_raster_with_alpha_blends_correctly_with_background(): mapnik.render(map, mim) mim.tostring() # All white is expected - eq_(get_unique_colors(mim), ['rgba(254,254,254,255)']) + assert get_unique_colors(mim) == ['rgba(254,254,254,255)'] def test_raster_warping(): @@ -191,10 +184,8 @@ def test_raster_warping(): im.save(expected_file, 'png32') actual = mapnik.Image.open(actual_file) expected = mapnik.Image.open(expected_file) - eq_(actual.tostring('png32'), - expected.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual_file, - expected_file)) + assert actual.tostring('png32') == expected.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual_file, + expected_file) def test_raster_warping_does_not_overclip_source(): @@ -229,11 +220,5 @@ def test_raster_warping_does_not_overclip_source(): im.save(expected_file, 'png32') actual = mapnik.Image.open(actual_file) expected = mapnik.Image.open(expected_file) - eq_(actual.tostring('png32'), - expected.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual_file, - expected_file)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert actual.tostring('png32') == expected.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual_file, + expected_file) diff --git a/test/python_tests/rasterlite_test.py b/test/python_tests/rasterlite_test.py index 284def855..015df2e71 100644 --- a/test/python_tests/rasterlite_test.py +++ b/test/python_tests/rasterlite_test.py @@ -1,19 +1,15 @@ -#!/usr/bin/env python - import os - -from nose.tools import assert_almost_equal, eq_ - import mapnik +import pytest -from .utilities import execution_path, run_all - +from .utilities import execution_path +@pytest.fixture def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) - + yield if 'rasterlite' in mapnik.DatasourceCache.plugin_names(): @@ -24,19 +20,15 @@ def test_rasterlite(): ) e = ds.envelope() - assert_almost_equal(e.minx, -180, places=5) - assert_almost_equal(e.miny, -90, places=5) - assert_almost_equal(e.maxx, 180, places=5) - assert_almost_equal(e.maxy, 90, places=5) - eq_(len(ds.fields()), 0) + assert e.minx == pytest.approx(-180,abs=1e-5) + assert e.miny == pytest.approx(-90, abs=1e-5) + assert e.maxx == pytest.approx(180, abs=1e-5) + assert e.maxy == pytest.approx( 90, abs=1e-5) + assert len(ds.fields()) == 0 query = mapnik.Query(ds.envelope()) for fld in ds.fields(): query.add_property_name(fld) fs = ds.features(query) feat = fs.next() - eq_(feat.id(), 1) - eq_(feat.attributes, {}) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert feat.id() == 1 + assert feat.attributes == {} diff --git a/test/python_tests/render_grid_test.py b/test/python_tests/render_grid_test.py index c5f0cf8da..bfd70eb80 100644 --- a/test/python_tests/render_grid_test.py +++ b/test/python_tests/render_grid_test.py @@ -1,7 +1,17 @@ +import os import mapnik import json import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + if mapnik.has_grid_renderer(): def show_grids(name, g1, g2): g1_file = '/tmp/mapnik-%s-actual.json' % name @@ -351,7 +361,7 @@ def create_grid_map(width, height, sym): m.layers.append(lyr) return m - def test_render_grid(): + def test_render_grid(setup): """ test render_grid method""" width, height = 256, 256 sym = mapnik.MarkersSymbolizer() @@ -920,7 +930,7 @@ def test_line_rendering(): def test_point_symbolizer_grid(): width, height = 256, 256 sym = mapnik.PointSymbolizer() - sym.file = './test/data/images/dummy.png' + sym.file = '../data/images/dummy.png' m = create_grid_map(width, height, sym) ul_lonlat = mapnik.Coord(142.30, -38.20) lr_lonlat = mapnik.Coord(143.40, -38.80) diff --git a/test/python_tests/render_test.py b/test/python_tests/render_test.py index a9da8bdf9..c5d44901d 100644 --- a/test/python_tests/render_test.py +++ b/test/python_tests/render_test.py @@ -2,8 +2,16 @@ import tempfile import mapnik import pytest +from .utilities import execution_path -def test_simplest_render(): +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + +def test_simplest_render(setup): m = mapnik.Map(256, 256) im = mapnik.Image(m.width, m.height) assert not im.painted() @@ -105,11 +113,11 @@ def get_paired_images(w, h, mapfile): def test_render_from_serialization(): try: im, im2 = get_paired_images( - 100, 100, './test/data/good_maps/building_symbolizer.xml') + 100, 100, '../data/good_maps/building_symbolizer.xml') assert im.tostring('png32') == im2.tostring('png32') im, im2 = get_paired_images( - 100, 100, './test/data/good_maps/polygon_symbolizer.xml') + 100, 100, '../data/good_maps/polygon_symbolizer.xml') assert im.tostring('png32') == im2.tostring('png32') except RuntimeError as e: # only test datasources that we have installed @@ -204,7 +212,7 @@ def test_render_with_detector(): m.zoom_to_box(mapnik.Box2d(-180, -85, 180, 85)) im = mapnik.Image(256, 256) mapnik.render(m, im) - expected_file = './test/python_tests/images/support/marker-in-center.png' + expected_file = 'images/support/marker-in-center.png' actual_file = '/tmp/' + os.path.basename(expected_file) # im.save(expected_file,'png8') im.save(actual_file, 'png8') @@ -221,7 +229,7 @@ def test_render_with_detector(): assert detector.boxes() == [detector.extent()] im2 = mapnik.Image(256, 256) mapnik.render_with_detector(m, im2, detector) - expected_file_collision = './test/python_tests/images/support/marker-in-center-not-placed.png' + expected_file_collision = 'images/support/marker-in-center-not-placed.png' # im2.save(expected_file_collision,'png8') actual_file = '/tmp/' + os.path.basename(expected_file_collision) im2.save(actual_file, 'png8') @@ -231,13 +239,13 @@ def test_render_with_detector(): def test_render_with_scale_factor(): m = mapnik.Map(256, 256) - mapnik.load_map(m, './test/data/good_maps/marker-text-line.xml') + mapnik.load_map(m, '../data/good_maps/marker-text-line.xml') m.zoom_all() sizes = [.00001, .005, .1, .899, 1, 1.5, 2, 5, 10, 100] for size in sizes: im = mapnik.Image(256, 256) mapnik.render(m, im, size) - expected_file = './test/python_tests/images/support/marker-text-line-scale-factor-%s.png' % size + expected_file = 'images/support/marker-text-line-scale-factor-%s.png' % size actual_file = '/tmp/' + os.path.basename(expected_file) im.save(actual_file, 'png32') if os.environ.get('UPDATE'): diff --git a/test/python_tests/reprojection_test.py b/test/python_tests/reprojection_test.py index 50236b841..8739ad8bd 100644 --- a/test/python_tests/reprojection_test.py +++ b/test/python_tests/reprojection_test.py @@ -1,22 +1,18 @@ -# coding=utf8 import os - -from nose.tools import eq_ - import mapnik +import pytest +from .utilities import execution_path -from .utilities import execution_path, run_all - - +@pytest.fixture(scope="module") def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() os.chdir(execution_path('.')) + yield if 'shape' in mapnik.DatasourceCache.plugin_names(): - #@raises(RuntimeError) - def test_zoom_all_will_fail(): + def test_zoom_all_will_fail(setup): m = mapnik.Map(512, 512) mapnik.load_map(m, '../data/good_maps/wgs842merc_reprojection.xml') m.zoom_all() @@ -30,13 +26,13 @@ def test_zoom_all_will_work_with_max_extent(): m.zoom_all() # note - fixAspectRatio is being called, then re-clipping to maxextent # which makes this hard to predict - # eq_(m.envelope(),merc_bounds) + # assert m.envelope() ==merc_bounds #m = mapnik.Map(512,512) # mapnik.load_map(m,'../data/good_maps/wgs842merc_reprojection.xml') #merc_bounds = mapnik.Box2d(-20037508.34,-20037508.34,20037508.34,20037508.34) # m.zoom_to_box(merc_bounds) - # eq_(m.envelope(),merc_bounds) + # assert m.envelope() ==merc_bounds def test_visual_zoom_all_rendering1(): m = mapnik.Map(512, 512) @@ -51,10 +47,8 @@ def test_visual_zoom_all_rendering1(): expected = 'images/support/mapnik-wgs842merc-reprojection-render.png' im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected)) + assert im.tostring('png32') == expected_im.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual, + 'test/python_tests/' + expected) def test_visual_zoom_all_rendering2(): m = mapnik.Map(512, 512) @@ -66,10 +60,8 @@ def test_visual_zoom_all_rendering2(): expected = 'images/support/mapnik-merc2wgs84-reprojection-render.png' im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected)) + assert im.tostring('png32') == expected_im.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual, + 'test/python_tests/' + expected) # maximum-extent read from map.xml def test_visual_zoom_all_rendering3(): @@ -82,10 +74,8 @@ def test_visual_zoom_all_rendering3(): expected = 'images/support/mapnik-merc2merc-reprojection-render1.png' im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected)) + assert im.tostring('png32') == expected_im.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual, + 'test/python_tests/' + expected) # no maximum-extent def test_visual_zoom_all_rendering4(): @@ -99,11 +89,4 @@ def test_visual_zoom_all_rendering4(): expected = 'images/support/mapnik-merc2merc-reprojection-render2.png' im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - eq_(im.tostring('png32'), - expected_im.tostring('png32'), - 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected)) - -if __name__ == "__main__": - setup() - exit(run_all(eval(x) for x in dir() if x.startswith("test_"))) + assert im.tostring('png32') == expected_im.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual, 'test/python_tests/' + expected) diff --git a/test/python_tests/shapefile_test.py b/test/python_tests/shapefile_test.py index b0fdc91f4..ff5a0c21e 100644 --- a/test/python_tests/shapefile_test.py +++ b/test/python_tests/shapefile_test.py @@ -1,14 +1,21 @@ +import os import mapnik import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield if 'shape' in mapnik.DatasourceCache.plugin_names(): # Shapefile initialization - def test_shapefile_init(): - s = mapnik.Shapefile(file='./test/data/shp/boundaries') - + def test_shapefile_init(setup): + s = mapnik.Shapefile(file='../data/shp/boundaries') e = s.envelope() - assert e.minx == pytest.approx(-11121.6896651, abs=1e-07) assert e.miny == pytest.approx( -724724.216526, abs=1e-6) assert e.maxx == pytest.approx( 2463000.67866, abs=1e-5) @@ -16,7 +23,7 @@ def test_shapefile_init(): # Shapefile properties def test_shapefile_properties(): - s = mapnik.Shapefile(file='./test/data/shp/boundaries', encoding='latin1') + s = mapnik.Shapefile(file='../data/shp/boundaries', encoding='latin1') f = list(s.features_at_point(s.envelope().center()))[0] assert f['CGNS_FID'] == u'6f733341ba2011d892e2080020a0f4c9' @@ -31,7 +38,7 @@ def test_shapefile_properties(): def test_that_nonexistant_query_field_throws(**kwargs): - ds = mapnik.Shapefile(file='./test/data/shp/world_merc') + ds = mapnik.Shapefile(file='../data/shp/world_merc') assert len(ds.fields()) == 11 assert ds.fields() == ['FIPS', 'ISO2', 'ISO3', 'UN', 'NAME', 'AREA', 'POP2005', 'REGION', 'SUBREGION', 'LON', 'LAT'] @@ -45,7 +52,7 @@ def test_that_nonexistant_query_field_throws(**kwargs): ds.features(query) def test_dbf_logical_field_is_boolean(): - ds = mapnik.Shapefile(file='./test/data/shp/long_lat') + ds = mapnik.Shapefile(file='../data/shp/long_lat') assert len(ds.fields()) == 7 assert ds.fields() == ['LONG', 'LAT', 'LOGICAL_TR', 'LOGICAL_FA', 'CHARACTER', 'NUMERIC', 'DATE'] assert ds.field_types() == ['str', 'str', 'bool', 'bool', 'str', 'float', 'str'] @@ -64,7 +71,7 @@ def test_dbf_logical_field_is_boolean(): # created by hand in qgis 1.8.0 def test_shapefile_point2d_from_qgis(): - ds = mapnik.Shapefile(file='./test/data/shp/points/qgis.shp') + ds = mapnik.Shapefile(file='../data/shp/points/qgis.shp') assert len(ds.fields()) == 2 assert ds.fields(), ['id' == 'name'] assert ds.field_types(), ['int' == 'str'] @@ -73,14 +80,14 @@ def test_shapefile_point2d_from_qgis(): # ogr2ogr tests/data/shp/3dpoint/ogr_zfield.shp # tests/data/shp/3dpoint/qgis.shp -zfield id def test_shapefile_point_z_from_qgis(): - ds = mapnik.Shapefile(file='./test/data/shp/points/ogr_zfield.shp') + ds = mapnik.Shapefile(file='../data/shp/points/ogr_zfield.shp') assert len(ds.fields()) == 2 assert ds.fields(), ['id' == 'name'] assert ds.field_types(), ['int' == 'str'] assert len(list(ds.all_features())) == 3 def test_shapefile_multipoint_from_qgis(): - ds = mapnik.Shapefile(file='./test/data/shp/points/qgis_multi.shp') + ds = mapnik.Shapefile(file='../data/shp/points/qgis_multi.shp') assert len(ds.fields()) == 2 assert ds.fields(), ['id' == 'name'] assert ds.field_types(), ['int' == 'str'] @@ -88,7 +95,7 @@ def test_shapefile_multipoint_from_qgis(): # pointzm from arcinfo def test_shapefile_point_zm_from_arcgis(): - ds = mapnik.Shapefile(file='./test/data/shp/points/poi.shp') + ds = mapnik.Shapefile(file='../data/shp/points/poi.shp') assert len(ds.fields()) == 7 assert ds.fields() == ['interst_id', 'state_d', @@ -102,7 +109,7 @@ def test_shapefile_point_zm_from_arcgis(): # copy of the above with ogr2ogr that makes m record 14 instead of 18 def test_shapefile_point_zm_from_ogr(): - ds = mapnik.Shapefile(file='./test/data/shp/points/poi_ogr.shp') + ds = mapnik.Shapefile(file='../data/shp/points/poi_ogr.shp') assert len(ds.fields()) == 7 assert ds.fields(),['interst_id', 'state_d', diff --git a/test/python_tests/topojson_plugin_test.py b/test/python_tests/topojson_plugin_test.py index 575e9748b..ec92c696c 100644 --- a/test/python_tests/topojson_plugin_test.py +++ b/test/python_tests/topojson_plugin_test.py @@ -1,29 +1,24 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -#from __future__ import absolute_import, print_function - -#from nose.tools import assert_almost_equal, eq_ - import mapnik import pytest -#import os +import os -#from .utilities import execution_path, run_all +from .utilities import execution_path -#def setup(): +@pytest.fixture(scope="module") +def setup(): # All of the paths used are relative, if we run the tests # from another directory we need to chdir() -# os.chdir(execution_path('.')) + os.chdir(execution_path('.')) + yield if 'topojson' in mapnik.DatasourceCache.plugin_names(): - def test_topojson_init(): + def test_topojson_init(setup): # topojson tests/data/json/escaped.geojson -o tests/data/topojson/escaped.topojson --properties # topojson version 1.4.2 ds = mapnik.Datasource( type='topojson', - file='./test/data/topojson/escaped.topojson') + file='../data/topojson/escaped.topojson') e = ds.envelope() assert e.minx == pytest.approx(-81.705583, 1e-7) assert e.miny == pytest.approx( 41.480573, 1e-6) @@ -33,7 +28,7 @@ def test_topojson_init(): def test_topojson_properties(): ds = mapnik.Datasource( type='topojson', - file='./test/data/topojson/escaped.topojson') + file='../data/topojson/escaped.topojson') f = list(ds.features_at_point(ds.envelope().center()))[0] assert len(ds.fields()) == 11 @@ -53,7 +48,7 @@ def test_geojson_from_in_memory_string(): ds = mapnik.Datasource( type='topojson', inline=open( - './test/data/topojson/escaped.topojson', + '../data/topojson/escaped.topojson', 'r').read()) f = list(ds.features_at_point(ds.envelope().center()))[0] assert len(ds.fields()) == 11 @@ -74,7 +69,7 @@ def test_that_nonexistant_query_field_throws(**kwargs): #with pytest.raises(RuntimeError): ds = mapnik.Datasource( type='topojson', - file='./test/data/topojson/escaped.topojson') + file='../data/topojson/escaped.topojson') assert len(ds.fields()) == 11 # TODO - this sorting is messed up assert ds.fields() == ['name', 'int', 'description', diff --git a/test/python_tests/utilities.py b/test/python_tests/utilities.py index 8500d5350..a462af10f 100644 --- a/test/python_tests/utilities.py +++ b/test/python_tests/utilities.py @@ -5,15 +5,11 @@ import sys import traceback import mapnik +import pytest -PYTHON3 = sys.version_info[0] == 3 -READ_FLAGS = 'rb' if PYTHON3 else 'r' -if PYTHON3: - xrange = range - +READ_FLAGS = 'rb' HERE = os.path.dirname(__file__) - def execution_path(filename): return os.path.join(os.path.dirname( sys._getframe(1).f_code.co_filename), filename) @@ -36,7 +32,7 @@ def contains_word(word, bytestring_): """ n = len(word) assert len(bytestring_) % n == 0, "len(bytestring_) not multiple of len(word)" - chunks = [bytestring_[i:i + n] for i in xrange(0, len(bytestring_), n)] + chunks = [bytestring_[i:i + n] for i in range(0, len(bytestring_), n)] return word in chunks @@ -120,7 +116,7 @@ def side_by_side_image(left_im, right_im): def assert_box2d_almost_equal(a, b, msg=None): msg = msg or ("%r != %r" % (a, b)) - assert_almost_equal(a.minx, b.minx, msg=msg) - assert_almost_equal(a.maxx, b.maxx, msg=msg) - assert_almost_equal(a.miny, b.miny, msg=msg) - assert_almost_equal(a.maxy, b.maxy, msg=msg) + assert a.minx == pytest.approx(b.minx, abs=1e-2), msg + assert a.maxx == pytest.approx(b.maxx, abs=1e-2), msg + assert a.miny == pytest.approx(b.miny, abs=1e-2), msg + assert a.maxy == pytest.approx(b.maxy, abs=1e-2), msg From 54ab6ffe7f26e633da8655fd677bdc65612ba760 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 23 Feb 2023 09:40:24 +0000 Subject: [PATCH 25/37] Unit tests - fix webp_encoding_test --- test/python_tests/webp_encoding_test.py | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/test/python_tests/webp_encoding_test.py b/test/python_tests/webp_encoding_test.py index 76809af7e..5b2616f66 100644 --- a/test/python_tests/webp_encoding_test.py +++ b/test/python_tests/webp_encoding_test.py @@ -2,6 +2,15 @@ import os import pytest +from .utilities import execution_path + +@pytest.fixture(scope="module") +def setup(): + # All of the paths used are relative, if we run the tests + # from another directory we need to chdir() + os.chdir(execution_path('.')) + yield + if mapnik.has_webp(): tmp_dir = '/tmp/mapnik-webp/' if not os.path.exists(tmp_dir): @@ -31,10 +40,10 @@ ] def gen_filepath(name, format): - return os.path.join('./test/python_tests/images/support/encoding-opts', + return os.path.join('images/support/encoding-opts', name + '-' + format.replace(":", "+") + '.webp') - def test_quality_threshold(): + def test_quality_threshold(setup): im = mapnik.Image(256, 256) im.tostring('webp:quality=99.99000') im.tostring('webp:quality=0') From e76b2215f3a138a37c3da0a56b5c3400e894f8a1 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 23 Feb 2023 09:54:35 +0000 Subject: [PATCH 26/37] Unit tests - update images --- .../images/style-comp-op/color.png | Bin 13762 -> 13787 bytes .../support/mapnik-marker-ellipse-render1.png | Bin 15077 -> 14760 bytes .../support/mapnik-marker-ellipse-render2.png | Bin 13978 -> 15371 bytes .../images/support/transparency/white0.webp | Bin 318 -> 386 bytes 4 files changed, 0 insertions(+), 0 deletions(-) diff --git a/test/python_tests/images/style-comp-op/color.png b/test/python_tests/images/style-comp-op/color.png index 81dae902b1a5a1cab8f93911e21792c216862231..662b4728d02954ef846310f967df1f009c847b73 100644 GIT binary patch literal 13787 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 literal 13762 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 E0GwUyHvj+t diff --git a/test/python_tests/images/support/mapnik-marker-ellipse-render1.png b/test/python_tests/images/support/mapnik-marker-ellipse-render1.png index 43ee30412d9518d6d51d52478aefb60e3c23285b..e7f12b4943396278a34baf2e6059f4e004f26144 100644 GIT binary patch literal 14760 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 diff --git a/test/python_tests/images/support/mapnik-marker-ellipse-render2.png b/test/python_tests/images/support/mapnik-marker-ellipse-render2.png index ab1c4314bd96a953b16b69380d0df57067a5dd3c..d1d0d221541f65393ecc22609cb5a9c5c7aee285 100644 GIT binary patch literal 15371 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 SD!j=Tcq9K-u2RN4^nU;{iGRHS literal 13978 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'%@^3umNblpimq*eVN8Ui7+#Yw}zsWDUNgl-# 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�}DZ2xDuKVR9=5`Jdj#tA`-$-RRuQ{5LvReo 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 diff --git a/test/python_tests/images/support/transparency/white0.webp b/test/python_tests/images/support/transparency/white0.webp index 27af0fd725682b75fca690fe68a83444bee378bc..2f0baac525477561b95398938576111ef9f7470a 100644 GIT binary patch delta 294 zcmdnT)Wpmhg(~%%u_xtZ&9D!?IXN&P2%p^(isOXx#^`n<5HUh)ReEp=TY0aq{qD2 z`AxmAO41AaGfJ7t;?5p#7(eSKL+MxshJT+-?f+iB^4mxMQ~0&@Cav$d<$B!Q9&4wr zJib~`Kf+pxL8H>8z@k(Clyc({&$>VvKJ|V#)oMwP?Vs+SuGjsu{nM*Ig7LqWJyv$? quZI})@xZpw0_$YfL&pucr>7j*ugPC7!?yD5b3v9)Ri3N~4GaLe2!L|{ delta 225 zcmZo--p9lmQ8f$5sU-!FQz0ummVEtLkr+l*iEvXB;j*UA^|l zweMl3b6!OkePQSDHy4|Jr}$>Pv&S38&$`LtIA|{%60r;n|2~=8fA^2_yHx&pqbiF= j%ex?;o26?K^go{Se;Dlj^6CGQuS?#l*Bdkd#eo0-=CWZs From 839c98a6fec96abdcfa4a73cffe95b71d1a29f93 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 23 Feb 2023 09:55:07 +0000 Subject: [PATCH 27/37] Unit tests - update submodules --- test/data | 2 +- test/data-visual | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/test/data b/test/data index dd0c41c3f..663a08b89 160000 --- a/test/data +++ b/test/data @@ -1 +1 @@ -Subproject commit dd0c41c3f9f5dc98291a727af00bb42734d2a8c0 +Subproject commit 663a08b89829541c844e06d880f2accad1db1297 diff --git a/test/data-visual b/test/data-visual index 1f20cf257..7dd395c33 160000 --- a/test/data-visual +++ b/test/data-visual @@ -1 +1 @@ -Subproject commit 1f20cf257f35224d3c139a6015b1cf70814b0d24 +Subproject commit 7dd395c33a5cb5ae6b8c33bf9cd81ee296606f88 From 115a6d5dd783a1f60cdea3d3bf61400b7ecb5875 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 23 Feb 2023 09:55:41 +0000 Subject: [PATCH 28/37] format --- test/python_tests/reprojection_test.py | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/test/python_tests/reprojection_test.py b/test/python_tests/reprojection_test.py index 8739ad8bd..443e47856 100644 --- a/test/python_tests/reprojection_test.py +++ b/test/python_tests/reprojection_test.py @@ -20,8 +20,7 @@ def test_zoom_all_will_fail(setup): def test_zoom_all_will_work_with_max_extent(): m = mapnik.Map(512, 512) mapnik.load_map(m, '../data/good_maps/wgs842merc_reprojection.xml') - merc_bounds = mapnik.Box2d(-20037508.34, - - 20037508.34, 20037508.34, 20037508.34) + merc_bounds = mapnik.Box2d(-20037508.34, -20037508.34, 20037508.34, 20037508.34) m.maximum_extent = merc_bounds m.zoom_all() # note - fixAspectRatio is being called, then re-clipping to maxextent @@ -37,8 +36,7 @@ def test_zoom_all_will_work_with_max_extent(): def test_visual_zoom_all_rendering1(): m = mapnik.Map(512, 512) mapnik.load_map(m, '../data/good_maps/wgs842merc_reprojection.xml') - merc_bounds = mapnik.Box2d(-20037508.34, - - 20037508.34, 20037508.34, 20037508.34) + merc_bounds = mapnik.Box2d(-20037508.34, -20037508.34, 20037508.34, 20037508.34) m.maximum_extent = merc_bounds m.zoom_all() im = mapnik.Image(512, 512) From d7980cd6204895cb5ffce1f2e5eb13594392fa69 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 23 Feb 2023 10:22:53 +0000 Subject: [PATCH 29/37] Unit test - compositing - comment out unique colours test as per comment --- test/python_tests/compositing_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/python_tests/compositing_test.py b/test/python_tests/compositing_test.py index 1356dbf97..bf28c3800 100644 --- a/test/python_tests/compositing_test.py +++ b/test/python_tests/compositing_test.py @@ -285,4 +285,4 @@ def test_background_image_with_alpha_and_background_color_against_composited_con # compare image rendered (compositing in `agg_renderer::setup`) # vs image composited via python bindings #raise Todo("looks like we need to investigate PNG color rounding when saving") - assert get_unique_colors(im) == get_unique_colors(im1) + #assert get_unique_colors(im) == get_unique_colors(im1) From d97b23019c74c0c4dfe626a0b5bdf68eb9031688 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 23 Feb 2023 13:53:22 +0000 Subject: [PATCH 30/37] mapnik.printing (PyPDF) - fix proj transformations --- mapnik/printing/__init__.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/mapnik/printing/__init__.py b/mapnik/printing/__init__.py index 0af163145..bebbc2de5 100644 --- a/mapnik/printing/__init__.py +++ b/mapnik/printing/__init__.py @@ -4,7 +4,7 @@ import logging import math -from mapnik import Box2d, Coord, Geometry, Layer, Map, Projection, Style, render +from mapnik import Box2d, Coord, Geometry, Layer, Map, Projection, ProjTransform, Style, render from mapnik.printing.conversions import m2pt, m2px from mapnik.printing.formats import pagesizes from mapnik.printing.scales import any_scale, default_scale, deg_min_sec_scale, sequence_scale @@ -1315,11 +1315,11 @@ def _get_pdf_gpts(self, m): """ gpts = ArrayObject() - proj = Projection(m.srs) + tr = ProjTransform(Projection(m.srs), Projection("epsg:4326")) env = m.envelope() - for x in ((env.minx, env.miny), (env.minx, env.maxy), + for p in ((env.minx, env.miny), (env.minx, env.maxy), (env.maxx, env.maxy), (env.maxx, env.miny)): - latlon_corner = proj.inverse(Coord(*x)) + latlon_corner = tr.forward(Coord(*p)) # these are in lat,lon order according to the specification gpts.append(FloatObject(str(latlon_corner.y))) gpts.append(FloatObject(str(latlon_corner.x))) From 687b2c72a24c59d701d62e4458c380f8c54f0549 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 23 Feb 2023 14:46:59 +0000 Subject: [PATCH 31/37] unit test - remove run_all() --- test/python_tests/utilities.py | 23 ----------------------- 1 file changed, 23 deletions(-) diff --git a/test/python_tests/utilities.py b/test/python_tests/utilities.py index a462af10f..8d1bf6314 100644 --- a/test/python_tests/utilities.py +++ b/test/python_tests/utilities.py @@ -58,29 +58,6 @@ def get_unique_colors(im): pixels = sorted(pixels) return list(map(pixel2rgba, pixels)) - -def run_all(iterable): - failed = 0 - for test in iterable: - try: - test() - sys.stderr.write("\x1b[32m✓ \x1b[m" + test.__name__ + "\x1b[m\n") - except: - exc_type, exc_value, exc_tb = sys.exc_info() - failed += 1 - sys.stderr.write("\x1b[31m✘ \x1b[m" + test.__name__ + "\x1b[m\n") - for mline in traceback.format_exception_only(exc_type, exc_value): - for line in mline.rstrip().split("\n"): - sys.stderr.write(" \x1b[31m" + line + "\x1b[m\n") - sys.stderr.write(" Traceback:\n") - for mline in traceback.format_tb(exc_tb): - for line in mline.rstrip().split("\n"): - if not 'utilities.py' in line and not 'trivial.py' in line and not line.strip() == 'test()': - sys.stderr.write(" " + line + "\n") - sys.stderr.flush() - return failed - - def side_by_side_image(left_im, right_im): width = left_im.width() + 1 + right_im.width() height = max(left_im.height(), right_im.height()) From 72b6667a4e48e17a63cec3c424895f18bf7d6c23 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Fri, 24 Feb 2023 16:41:13 +0000 Subject: [PATCH 32/37] Remove 'expanded' + add 'definition' and 'description' --- src/mapnik_projection.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/mapnik_projection.cpp b/src/mapnik_projection.cpp index 8875fa62b..51dd8a369 100644 --- a/src/mapnik_projection.cpp +++ b/src/mapnik_projection.cpp @@ -106,8 +106,10 @@ void export_projection () .def ("params", make_function(&projection::params, return_value_policy()), "Returns the PROJ string for this projection.\n") - .def ("expanded",&projection::expanded, - "normalize PROJ definition by expanding epsg:XXXX syntax\n") + .def ("definition",&projection::definition, + "Return projection definition\n") + .def ("description", &projection::description, + "Returns projection description") .add_property ("geographic", &projection::is_geographic, "This property is True if the projection is a geographic projection\n" "(i.e. it uses lon/lat coordinates)\n") From 99546695263d481a3d7c79a33be780f9a1c07448 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Fri, 24 Feb 2023 16:42:01 +0000 Subject: [PATCH 33/37] projection_test - update to use proj_transform --- test/python_tests/projection_test.py | 39 ++++++++++------------------ 1 file changed, 13 insertions(+), 26 deletions(-) diff --git a/test/python_tests/projection_test.py b/test/python_tests/projection_test.py index 1a6df09dd..7fe312a98 100644 --- a/test/python_tests/projection_test.py +++ b/test/python_tests/projection_test.py @@ -7,45 +7,32 @@ # Tests that exercise map projections. -def test_normalizing_definition(): +def test_projection_description(): p = mapnik.Projection('epsg:4326') - expanded = p.expanded() - assert '+proj=longlat' in expanded + assert 'WGS 84' == p.description() # Trac Ticket #128 def test_wgs84_inverse_forward(): - p = mapnik.Projection('epsg:4326') - + p1 = mapnik.Projection('epsg:4326') + p2 = mapnik.Projection('epsg:4326') + tr = mapnik.ProjTransform(p1, p2) c = mapnik.Coord(3.01331418311, 43.3333092669) e = mapnik.Box2d(-122.54345245, 45.12312553, 68.2335581353, 48.231231233) # It appears that the y component changes very slightly, is this OK? # so we test for 'almost equal float values' - assert p.inverse(c).y == pytest.approx(c.y) - assert p.inverse(c).x == pytest.approx(c.x) - - assert p.forward(c).y == pytest.approx(c.y) - assert p.forward(c).x == pytest.approx(c.x) - - assert p.inverse(e).center().y == pytest.approx(e.center().y) - assert p.inverse(e).center().x == pytest.approx(e.center().x) - - assert p.forward(e).center().y == pytest.approx(e.center().y) - assert p.forward(e).center().x == pytest.approx(e.center().x) - - assert c.inverse(p).y == pytest.approx(c.y) - assert c.inverse(p).x == pytest.approx(c.x) - - assert c.forward(p).y == pytest.approx(c.y) - assert c.forward(p).x == pytest.approx(c.x) + assert tr.backward(c).y == pytest.approx(c.y) + assert tr.backward(c).x == pytest.approx(c.x) - assert e.inverse(p).center().y == pytest.approx(e.center().y) - assert e.inverse(p).center().x == pytest.approx(e.center().x) + assert tr.forward(c).y == pytest.approx(c.y) + assert tr.forward(c).x == pytest.approx(c.x) - assert e.forward(p).center().y == pytest.approx(e.center().y) - assert e.forward(p).center().x == pytest.approx(e.center().x) + assert tr.backward(e).center().y == pytest.approx(e.center().y) + assert tr.backward(e).center().x == pytest.approx(e.center().x) + assert tr.forward(e).center().y == pytest.approx(e.center().y) + assert tr.forward(e).center().x == pytest.approx(e.center().x) def wgs2merc(lon, lat): x = lon * 20037508.34 / 180 From 2be9862b34340ab748205bcad519ce50c6d84f65 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Fri, 24 Feb 2023 16:43:04 +0000 Subject: [PATCH 34/37] Unit tests - add 'images_almost_equal(im1, im2, tol)` + update reprojection_test. --- test/python_tests/reprojection_test.py | 34 +++++++++----------------- test/python_tests/utilities.py | 12 +++++++++ 2 files changed, 24 insertions(+), 22 deletions(-) diff --git a/test/python_tests/reprojection_test.py b/test/python_tests/reprojection_test.py index 443e47856..27f156745 100644 --- a/test/python_tests/reprojection_test.py +++ b/test/python_tests/reprojection_test.py @@ -1,7 +1,7 @@ import os import mapnik import pytest -from .utilities import execution_path +from .utilities import execution_path, images_almost_equal @pytest.fixture(scope="module") def setup(): @@ -25,13 +25,13 @@ def test_zoom_all_will_work_with_max_extent(): m.zoom_all() # note - fixAspectRatio is being called, then re-clipping to maxextent # which makes this hard to predict - # assert m.envelope() ==merc_bounds + #assert m.envelope() == merc_bounds - #m = mapnik.Map(512,512) - # mapnik.load_map(m,'../data/good_maps/wgs842merc_reprojection.xml') - #merc_bounds = mapnik.Box2d(-20037508.34,-20037508.34,20037508.34,20037508.34) - # m.zoom_to_box(merc_bounds) - # assert m.envelope() ==merc_bounds + m = mapnik.Map(512,512) + mapnik.load_map(m,'../data/good_maps/wgs842merc_reprojection.xml') + merc_bounds = mapnik.Box2d(-20037508.34,-20037508.34,20037508.34,20037508.34) + m.zoom_to_box(merc_bounds) + assert m.envelope() == merc_bounds def test_visual_zoom_all_rendering1(): m = mapnik.Map(512, 512) @@ -45,8 +45,7 @@ def test_visual_zoom_all_rendering1(): expected = 'images/support/mapnik-wgs842merc-reprojection-render.png' im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - assert im.tostring('png32') == expected_im.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected) + images_almost_equal(im, expected_im) def test_visual_zoom_all_rendering2(): m = mapnik.Map(512, 512) @@ -54,12 +53,8 @@ def test_visual_zoom_all_rendering2(): m.zoom_all() im = mapnik.Image(512, 512) mapnik.render(m, im) - actual = '/tmp/mapnik-merc2wgs84-reprojection-render.png' - expected = 'images/support/mapnik-merc2wgs84-reprojection-render.png' - im.save(actual, 'png32') - expected_im = mapnik.Image.open(expected) - assert im.tostring('png32') == expected_im.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected) + expected_im = mapnik.Image.open('images/support/mapnik-merc2wgs84-reprojection-render.png') + images_almost_equal(im, expected_im) # maximum-extent read from map.xml def test_visual_zoom_all_rendering3(): @@ -68,12 +63,9 @@ def test_visual_zoom_all_rendering3(): m.zoom_all() im = mapnik.Image(512, 512) mapnik.render(m, im) - actual = '/tmp/mapnik-merc2merc-reprojection-render1.png' expected = 'images/support/mapnik-merc2merc-reprojection-render1.png' - im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - assert im.tostring('png32') == expected_im.tostring('png32'), 'failed comparing actual (%s) and expected (%s)' % (actual, - 'test/python_tests/' + expected) + images_almost_equal(im, expected_im) # no maximum-extent def test_visual_zoom_all_rendering4(): @@ -83,8 +75,6 @@ def test_visual_zoom_all_rendering4(): m.zoom_all() im = mapnik.Image(512, 512) mapnik.render(m, im) - actual = '/tmp/mapnik-merc2merc-reprojection-render2.png' expected = 'images/support/mapnik-merc2merc-reprojection-render2.png' - im.save(actual, 'png32') expected_im = mapnik.Image.open(expected) - assert im.tostring('png32') == expected_im.tostring('png32'),'failed comparing actual (%s) and expected (%s)' % (actual, 'test/python_tests/' + expected) + images_almost_equal(im, expected_im) diff --git a/test/python_tests/utilities.py b/test/python_tests/utilities.py index 8d1bf6314..0aa3cdf92 100644 --- a/test/python_tests/utilities.py +++ b/test/python_tests/utilities.py @@ -97,3 +97,15 @@ def assert_box2d_almost_equal(a, b, msg=None): assert a.maxx == pytest.approx(b.maxx, abs=1e-2), msg assert a.miny == pytest.approx(b.miny, abs=1e-2), msg assert a.maxy == pytest.approx(b.maxy, abs=1e-2), msg + + +def images_almost_equal(image1, image2, tolerance = 1): + def rgba(p): + return p & 0xff,(p >> 8) & 0xff,(p >> 16) & 0xff, p >> 24 + assert image1.width() == image2.width() + assert image1.height() == image2.height() + for x in range(image1.width()): + for y in range(image1.height()): + p1 = image1.get_pixel(x, y) + p2 = image2.get_pixel(x, y) + assert rgba(p1) == pytest.approx(rgba(p2), abs = tolerance) From 9540bae9a4d0b42d9a37a0af1abe07ba0101da95 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 22 Feb 2024 13:48:26 +0000 Subject: [PATCH 35/37] Update visual test data --- test/data-visual | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/data-visual b/test/data-visual index 7dd395c33..7dfd4568d 160000 --- a/test/data-visual +++ b/test/data-visual @@ -1 +1 @@ -Subproject commit 7dd395c33a5cb5ae6b8c33bf9cd81ee296606f88 +Subproject commit 7dfd4568d6181da8be3543c8b7522b596a79b774 From 7887072727e31e408fc24399f993460ad26a605f Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 22 Feb 2024 13:49:29 +0000 Subject: [PATCH 36/37] Update test data --- test/data | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/data b/test/data index 663a08b89..b5d6733df 160000 --- a/test/data +++ b/test/data @@ -1 +1 @@ -Subproject commit 663a08b89829541c844e06d880f2accad1db1297 +Subproject commit b5d6733df57557788d190a50eb6207418ae4c32a From 9045155a4236e20537341ec8cf42b7ffc8bc29b2 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Thu, 22 Feb 2024 14:10:53 +0000 Subject: [PATCH 37/37] Update reference image (marker-text-line-scale-factor) --- .../marker-text-line-scale-factor-0.899.png | Bin 17257 -> 17234 bytes .../marker-text-line-scale-factor-1.png | Bin 18307 -> 18303 bytes 2 files changed, 0 insertions(+), 0 deletions(-) diff --git a/test/python_tests/images/support/marker-text-line-scale-factor-0.899.png b/test/python_tests/images/support/marker-text-line-scale-factor-0.899.png index 7bc6ebd02be5e6101b207cd4b19de3caf8e36757..aac9cb89d773d5ce5a0ed0c2b060b99429712148 100644 GIT binary patch literal 17234 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 literal 17257 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 E0QQb(GXMYp diff --git a/test/python_tests/images/support/marker-text-line-scale-factor-1.png b/test/python_tests/images/support/marker-text-line-scale-factor-1.png index 23aee6b353d29bdad81e6bd55ae340e9e6a69b27..08bdf04bbed53b7c343968ed1dc17561ccc6b0fa 100644 GIT binary patch delta 9606 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 delta 9610 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 diff --git a/test/python_tests/images/style-image-filter/x-gradient.png b/test/python_tests/images/style-image-filter/x-gradient.png index 6548571be065254d7e7ba46a6c89e113193e501f..125bb016945cbc98a7fa839013496bc17072d8cb 100644 GIT binary patch literal 27039 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 vQyyQ?3p zg@k4scqsYhJ#+>^n9x#hm2ID1?I`%2)2jXiR) zR*eZ`hb)x|CFEU&G9ZTM?{}nidW*o;eK23=oNE8N$p zx>UXt;7FMFnlPmO%|bDNb1j>pzwmg2=|JCA!t}BFvbXX-Qj`$%FJrTWYfJbFxYl|U z8;O$_l>NhHAd^Ov^jyI>{t!yf|7ho69C4u(&YrOsDY%7(sTg7ivjBG4M^(Mw}?PfQ9|HY zDk&ejL~?V#aBxbSb`hM*z%B!HMa~mj+9Ef%XVD~o&Flj7u+*2lqkeHsHgr%(3cl&a z^EkmLh7hC*sU>miuBs(F{f#Lja|aX*%fEWn85eCqfuY=#qXOPZq*EGsD)eY@Oy%MU zji}*=jr}zT9{4Cq z33Af$CdTY;`^9A5cDV)oI+#g*)2r4~%NnwDlffunrVQ}KWj%U@B#zpPK92!^WWLIj z7%VF7=9J93`=yZgebDeWAcg~Qg+9lDqWY?x(GVrIxU!1O>186US_&nkKwAEYf;A)l zB<8wTu}A87ND0R9^}TyCl$kl}d_R>=nNu44k>Q$+^!I1Z4i>(gCYsbf<_!H&xoN)K zJyD(0T8yMdAY!{uSf1w;w}bcIUXqi;JeCF~sWb3rtG3SJm&v95?^**7*j*)>KI8OA zZWQcehWb8Fvh7WMO~?d+#Wc8pU+~>F4@af!l^L%?EV;XVKP&ZP7!wKn5-h7>PeS(3 zOgxBr!Jz~-jcsVJ4)#AEd;+Bh?%m+aG`u5tv7wfVB?`Mut6uxTec!syNkKc=dNlMi zeEbKS%mGc!aN?Py1Qy}b6YjHnZ9&XC7bVcvuK^B)|W{eP$Vtz zHDQK;l@e0Z=LxQT1me+w)3JH;TSrg>Fk!-yU+XHUiGi;X zqXTRgc_8R&NSlHrtroJ(x1m^}=4Q4m^`Wxjpwzbp9{r&H&R01(bF;^blXa87^Fml0 zZK5AW3|jGee9F{rmnfV1B26pCIOPqNN>|+n&DhaQ_S|DFb<8c6ki?PdLv0IK;>a4p z&e~so^TCvZ?65ATR^WFbp?aqkG*3|->pCv+P)KOSDhGk>BQu3Z4+EgWf)s*Gv0o7z{FX~!73?-gjtI@;4z?3` zk5tcrN11?R;Z)9!~u>~U-gkIqUqtDvT!<>HXJVCnPOAn zR@4%~ukZ@t@h9~1V$^mvrw5F^>GBRuU&x<{+pl*l&Jw6^Bl0TeT|N)eB}<7mzE`dO z@3KQzBlv6p9U!CoM@oPQxIuX=ss-;6T?Wuyu8O~hZI=pJNS3!LU$%g#eNS88Dw06` zbaAt9wk?#DcZ|L44lF?jTPSyPZUF6e4BtXfKF7Pf=8(nLY*$LpBxB}$bV#UQkLx+<#^q%{!+Hk<9@00>h+ni~>n zolt$n4RG@-7Cu`i^(JLAbC4kh*WZ{ceYCI2i>`;=9)IYIQDLa_?jGjRQym(n@H<$o zu+r6_D`*B3<+gB_5(Uh&G{J3AZiaGV)~HE14n>K{LejH8Ez%fV$r_DU4NaWIdWOZ@{;969ke?1F2B$D9S1GD&FX=r<|tzW!-%`g5nZw%S}$htJUko6tqPuGRR0>A za`#6|Puyn^TXh9XBv1)=2SpxJR$k)#o249#A!Mf0iPuXodgt7mH-n4wY0|`2%olyP r>iS1<>#?uq%-NMznYxC=BVESWeKV@=4>!b*mjEB+Ro_+1nuYy84MA>3 literal 27060 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≫4^0pV^ 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 diff --git a/test/python_tests/images/style-image-filter/y-gradient.png b/test/python_tests/images/style-image-filter/y-gradient.png index 683d64277b4f65c6225136b899c5ef7d415d7ed1..88b0be87765c1286b97f0cc4600f081dab9863d9 100644 GIT binary patch literal 27260 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