add new enumerate type to replace zorder

master
Oliver Tonnhofer 2015-08-25 14:52:09 +02:00
parent 2b2d534082
commit 9e125aee02
7 changed files with 266 additions and 119 deletions

View File

@ -205,6 +205,32 @@ Convert ``true``, ``yes`` and ``1`` to the numeric ``1``, ``-1`` values to ``-1`
Convert values to an integer number. Other values will not be inserted. Useful for ``admin_levels`` for example. Convert values to an integer number. Other values will not be inserted. Useful for ``admin_levels`` for example.
``enumerate``
^^^^^^^^^^^^^
Enumerates a list of values and stores tag values as an integer.
The following `enum` column will contain ``1`` for ``landuse=forest``, ``4`` for ``landuse=grass`` and ``0`` for undefined values.
.. code-block:: javascript
{
"args": {
"values": [
"forest",
"park",
"cemetery",
"grass"
]
},
"type": "enumerate",
"name": "enum",
"key": "landuse"
}
``mapping_value`` will be used when ``key`` is not set or ``null``.
Element types Element types
~~~~~~~~~~~~~ ~~~~~~~~~~~~~
@ -255,7 +281,6 @@ Area of polygon geometries in square meters. This area is calculated in the webm
Calculate the z-order of an OSM highway or railway. Returns a numeric value that represents the importance of a way where ``motorway`` is the most important (9), and ``path`` or ``track`` are least important (0). ``bridge`` and ``tunnel`` will modify the value by -10/+10. ``layer`` will be multiplied by ten and added to the value. E.g. ``highway=motorway``, ``bridge=yes`` and ``layer=2`` will return 39 (9+10+2*10). Calculate the z-order of an OSM highway or railway. Returns a numeric value that represents the importance of a way where ``motorway`` is the most important (9), and ``path`` or ``track`` are least important (0). ``bridge`` and ``tunnel`` will modify the value by -10/+10. ``layer`` will be multiplied by ten and added to the value. E.g. ``highway=motorway``, ``bridge=yes`` and ``layer=2`` will return 39 (9+10+2*10).
``hstore_tags`` ``hstore_tags``
^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^

View File

@ -71,58 +71,57 @@
}, },
{ {
"args": { "args": {
"ranks": [ "values": [
"pedestrian", "land",
"footway",
"playground",
"park",
"forest",
"cemetery",
"farmyard",
"farm",
"farmland",
"wood",
"meadow",
"grass",
"wetland",
"village_green",
"recreation_ground",
"garden",
"sports_centre",
"pitch",
"common",
"allotments",
"golf_course",
"university",
"school",
"college",
"library",
"baracks",
"fuel",
"parking",
"nature_reserve",
"cinema",
"theatre",
"place_of_worship",
"hospital",
"scrub",
"orchard",
"vineyard",
"zoo",
"quarry",
"residential",
"retail",
"commercial",
"industrial",
"railway",
"heath",
"island", "island",
"land" "heath",
"railway",
"industrial",
"commercial",
"retail",
"residential",
"quarry",
"zoo",
"vineyard",
"orchard",
"scrub",
"hospital",
"place_of_worship",
"theatre",
"cinema",
"nature_reserve",
"parking",
"fuel",
"baracks",
"library",
"college",
"school",
"university",
"golf_course",
"allotments",
"common",
"pitch",
"sports_centre",
"garden",
"recreation_ground",
"village_green",
"wetland",
"grass",
"meadow",
"wood",
"farmland",
"farm",
"farmyard",
"cemetery",
"forest",
"park",
"playground",
"footway",
"pedestrian"
] ]
}, },
"type": "zorder", "type": "enumerate",
"name": "z_order", "name": "z_order"
"key": "z_order"
} }
], ],
"type": "polygon", "type": "polygon",
@ -258,22 +257,21 @@
}, },
{ {
"args": { "args": {
"ranks": [ "values": [
"country", "locality",
"state",
"region",
"county",
"city",
"town",
"village",
"hamlet",
"suburb", "suburb",
"locality" "hamlet",
"village",
"town",
"city",
"county",
"region",
"state",
"country"
] ]
}, },
"type": "zorder", "type": "enumerate",
"name": "z_order", "name": "z_order"
"key": "z_order"
}, },
{ {
"type": "integer", "type": "integer",

View File

@ -31,6 +31,7 @@ func init() {
"wayzorder": {"wayzorder", "int32", WayZOrder, nil}, "wayzorder": {"wayzorder", "int32", WayZOrder, nil},
"pseudoarea": {"pseudoarea", "float32", PseudoArea, nil}, "pseudoarea": {"pseudoarea", "float32", PseudoArea, nil},
"zorder": {"zorder", "int32", nil, MakeZOrder}, "zorder": {"zorder", "int32", nil, MakeZOrder},
"enumerate": {"enumerate", "int32", nil, MakeEnumerate},
"string_suffixreplace": {"string_suffixreplace", "string", nil, MakeSuffixReplace}, "string_suffixreplace": {"string_suffixreplace", "string", nil, MakeSuffixReplace},
} }
} }
@ -224,6 +225,7 @@ func WayZOrder(val string, elem *element.OSMElem, geom *geom.Geometry, match Mat
} }
func MakeZOrder(fieldName string, fieldType FieldType, field Field) (MakeValue, error) { func MakeZOrder(fieldName string, fieldType FieldType, field Field) (MakeValue, error) {
log.Print("warn: zorder type is deprecated and will be removed. See enumerate type.")
_rankList, ok := field.Args["ranks"] _rankList, ok := field.Args["ranks"]
if !ok { if !ok {
return nil, errors.New("missing ranks in args for zorder") return nil, errors.New("missing ranks in args for zorder")
@ -269,6 +271,42 @@ func MakeZOrder(fieldName string, fieldType FieldType, field Field) (MakeValue,
return zOrder, nil return zOrder, nil
} }
func MakeEnumerate(fieldName string, fieldType FieldType, field Field) (MakeValue, error) {
_valuesList, ok := field.Args["values"]
if !ok {
return nil, errors.New("missing values in args for enumerate")
}
valuesList, ok := _valuesList.([]interface{})
if !ok {
return nil, errors.New("values in args for enumerate not a list")
}
values := make(map[string]int)
for i, value := range valuesList {
valueName, ok := value.(string)
if !ok {
return nil, errors.New("value in values not a string")
}
values[valueName] = i + 1
}
enumerate := func(val string, elem *element.OSMElem, geom *geom.Geometry, match Match) interface{} {
if field.Key != "" {
if r, ok := values[val]; ok {
return r
}
return 0
}
if r, ok := values[match.Value]; ok {
return r
}
return 0
}
return enumerate, nil
}
func MakeSuffixReplace(fieldName string, fieldType FieldType, field Field) (MakeValue, error) { func MakeSuffixReplace(fieldName string, fieldType FieldType, field Field) (MakeValue, error) {
_changes, ok := field.Args["suffixes"] _changes, ok := field.Args["suffixes"]
if !ok { if !ok {

View File

@ -107,6 +107,80 @@ func TestZOrder(t *testing.T) {
} }
} }
func TestEnumerate_Match(t *testing.T) {
// test enumerate by matched mapping key
match := Match{}
zOrder, err := MakeEnumerate("enumerate",
AvailableFieldTypes["enumerate"],
Field{
Name: "enumerate",
Key: "",
Type: "enumerate",
Args: map[string]interface{}{"values": []interface{}{"AA", "CC", "FF", "ZZ"}},
},
)
if err != nil {
t.Fatal(err)
}
elem := &element.OSMElem{}
elem.Tags = element.Tags{} // missing
if v := zOrder("", elem, nil, match); v != 0 {
t.Errorf(" -> %v", v)
}
match.Value = "ABCD" // unknown
if v := zOrder("", elem, nil, match); v != 0 {
t.Errorf(" -> %v", v)
}
match.Value = "AA"
if v := zOrder("", elem, nil, match); v != 1 {
t.Errorf(" -> %v", v)
}
match.Value = "CC"
if v := zOrder("", elem, nil, match); v != 2 {
t.Errorf(" -> %v", v)
}
match.Value = "ZZ"
if v := zOrder("", elem, nil, match); v != 4 {
t.Errorf(" -> %v", v)
}
}
func TestEnumerate_Key(t *testing.T) {
// test enumerate by key
match := Match{}
zOrder, err := MakeEnumerate("enumerate",
AvailableFieldTypes["enumerate"],
Field{
Name: "enumerate",
Key: "fips",
Type: "enumerate",
Args: map[string]interface{}{"values": []interface{}{"AA", "CC", "FF", "ZZ"}},
},
)
if err != nil {
t.Fatal(err)
}
elem := &element.OSMElem{}
if v := zOrder("", elem, nil, match); v != 0 {
t.Errorf(" -> %v", v)
}
if v := zOrder("ABCD", elem, nil, match); v != 0 {
t.Errorf(" -> %v", v)
}
if v := zOrder("AA", elem, nil, match); v != 1 {
t.Errorf(" -> %v", v)
}
if v := zOrder("CC", elem, nil, match); v != 2 {
t.Errorf(" -> %v", v)
}
if v := zOrder("ZZ", elem, nil, match); v != 4 {
t.Errorf(" -> %v", v)
}
}
func TestMakeSuffixReplace(t *testing.T) { func TestMakeSuffixReplace(t *testing.T) {
field := Field{ field := Field{
Name: "name", Key: "name", Type: "string_suffixreplace", Name: "name", Key: "name", Type: "string_suffixreplace",

View File

@ -1021,4 +1021,36 @@
</node> </node>
<node id="70002" version="1" timestamp="2011-11-11T00:11:11Z" lat="0.02" lon="20.00"/> <node id="70002" version="1" timestamp="2011-11-11T00:11:11Z" lat="0.02" lon="20.00"/>
<node id="100001" version="1" timestamp="2011-11-11T00:11:11Z" lat="80.01" lon="-40.00"/>
<node id="100002" version="1" timestamp="2011-11-11T00:11:11Z" lat="80.00" lon="-40.01"/>
<node id="100003" version="1" timestamp="2011-11-11T00:11:11Z" lat="80.01" lon="-40.02"/>
<way id="100001" version="1" timestamp="2011-11-11T00:11:11Z">
<nd ref="100001"/>
<nd ref="100002"/>
<nd ref="100003"/>
<nd ref="100001"/>
<tag k="name" v="way 100001"/>
<tag k="enum_test" v="park"/>
<tag k="landuse" v="park"/>
</way>
<way id="100002" version="1" timestamp="2011-11-11T00:11:11Z">
<nd ref="100001"/>
<nd ref="100002"/>
<nd ref="100003"/>
<nd ref="100001"/>
<tag k="name" v="way 100002"/>
<tag k="enum_test" v="unknown"/>
<tag k="landuse" v="park"/>
</way>
<way id="100003" version="1" timestamp="2011-11-11T00:11:11Z">
<nd ref="100001"/>
<nd ref="100002"/>
<nd ref="100003"/>
<nd ref="100001"/>
<tag k="name" v="way 100003"/>
<tag k="enum_test" v="wood"/>
<tag k="landuse" v="wood"/>
</way>
</osm> </osm>

View File

@ -71,58 +71,32 @@
}, },
{ {
"args": { "args": {
"ranks": [ "values": [
"pedestrian",
"footway",
"playground",
"park", "park",
"forest", "forest",
"cemetery",
"farmyard",
"farm",
"farmland",
"wood",
"meadow",
"grass",
"wetland",
"village_green",
"recreation_ground",
"garden",
"sports_centre",
"pitch",
"common",
"allotments",
"golf_course",
"university",
"school",
"college",
"library",
"baracks",
"fuel",
"parking",
"nature_reserve",
"cinema",
"theatre",
"place_of_worship",
"hospital",
"scrub",
"orchard",
"vineyard",
"zoo",
"quarry",
"residential", "residential",
"retail", "retail",
"commercial", "commercial",
"industrial", "industrial",
"railway", "railway",
"heath", "cemetery",
"island", "grass",
"land" "farmyard",
"farm",
"farmland",
"orchard",
"vineyard",
"wood",
"meadow",
"village_green",
"recreation_ground",
"allotments",
"quarry"
] ]
}, },
"type": "zorder", "type": "enumerate",
"name": "z_order", "name": "enum",
"key": "z_order" "key": "enum_test"
} }
], ],
"type": "polygon", "type": "polygon",
@ -258,22 +232,21 @@
}, },
{ {
"args": { "args": {
"ranks": [ "values": [
"country", "locality",
"state",
"region",
"county",
"city",
"town",
"village",
"hamlet",
"suburb", "suburb",
"locality" "hamlet",
"village",
"town",
"city",
"county",
"region",
"state",
"country"
] ]
}, },
"type": "zorder", "type": "enumerate",
"name": "z_order", "name": "z_order"
"key": "z_order"
}, },
{ {
"type": "integer", "type": "integer",

View File

@ -298,6 +298,13 @@ def test_update_node_to_coord_1():
assert t.query_row(t.db_conf, 'osm_amenities', 70001) assert t.query_row(t.db_conf, 'osm_amenities', 70001)
assert not t.query_row(t.db_conf, 'osm_amenities', 70002) assert not t.query_row(t.db_conf, 'osm_amenities', 70002)
def test_enumerate_key():
"""Enumerate from key."""
assert t.query_row(t.db_conf, 'osm_landusages', 100001)['enum'] == 1
assert t.query_row(t.db_conf, 'osm_landusages', 100002)['enum'] == 0
assert t.query_row(t.db_conf, 'osm_landusages', 100003)['enum'] == 15
####################################################################### #######################################################################
def test_update(): def test_update():
"""Diff import applies""" """Diff import applies"""