diff --git a/docs/mapping.rst b/docs/mapping.rst index 0ff0e64..7330fc8 100644 --- a/docs/mapping.rst +++ b/docs/mapping.rst @@ -22,7 +22,7 @@ The most important part is the ``tables`` definition. Each table is a YAML objec ~~~~~~~~~~~ ``mapping`` defines which OSM key/values an element needs to have to be imported into this table. ``mapping`` is a YAML object with the OSM `key` as the object key and a list of all OSM `values` to be matched as the object value. -You can use the value ``__any__`` to match all values. +You can use ``__any__`` to match all values (e.g. ``amenity: [__any__]``). To match elements regardless of their tags use ``__any__: [__any__]``. You need to use :ref:`load_all` in this case so that Imposm has access to all tags. To import all polygons with `tourism=zoo`, `natural=wood` or `natural=land` into the ``landusages`` table: diff --git a/mapping/matcher.go b/mapping/matcher.go index d5675bb..2dcd4da 100644 --- a/mapping/matcher.go +++ b/mapping/matcher.go @@ -127,7 +127,10 @@ func (tm *tagMatcher) match(tags *element.Tags) []Match { } tables[t.DestTable] = this } + } + if values, ok := tm.mappings[Key("__any__")]; ok { + addTables("__any__", "__any__", values["__any__"]) } for k, v := range *tags { diff --git a/test/any_any.osm b/test/any_any.osm new file mode 100644 index 0000000..388dd8e --- /dev/null +++ b/test/any_any.osm @@ -0,0 +1,21 @@ + + + + + + + + + + + + + + + + + + + + + diff --git a/test/any_any_mapping.json b/test/any_any_mapping.json new file mode 100644 index 0000000..5e060ed --- /dev/null +++ b/test/any_any_mapping.json @@ -0,0 +1,56 @@ +{ + "tags": { + "load_all": true, + "exclude": [ + "created_by", + "source" + ] + }, + "tables": { + "all": { + "fields": [ + { + "type": "id", + "name": "osm_id" + }, + { + "type": "geometry", + "name": "geometry" + }, + { + "type": "hstore_tags", + "name": "tags" + } + ], + "type": "point", + "mapping": { + "__any__": ["__any__"] + } + }, + "amenities": { + "fields": [ + { + "type": "id", + "name": "osm_id" + }, + { + "type": "geometry", + "name": "geometry" + }, + { + "type": "hstore_tags", + "name": "tags" + }, + { + "type": "mapping_value", + "name": "type" + }, + ], + "type": "point", + "mapping": { + "amenity": ["__any__"] + } + } + + } +} diff --git a/test/any_any_test.go b/test/any_any_test.go new file mode 100644 index 0000000..13161aa --- /dev/null +++ b/test/any_any_test.go @@ -0,0 +1,49 @@ +package test + +import ( + "database/sql" + + "testing" + + "github.com/omniscale/imposm3/geom/geos" +) + +func TestAnyAny_Prepare(t *testing.T) { + ts.dir = "/tmp/imposm3test" + ts.config = importConfig{ + connection: "postgis://", + cacheDir: ts.dir, + osmFileName: "build/any_any.pbf", + mappingFileName: "any_any_mapping.json", + } + ts.g = geos.NewGeos() + + var err error + ts.db, err = sql.Open("postgres", "sslmode=disable") + if err != nil { + t.Fatal(err) + } + ts.dropSchemas() +} + +func TestAnyAny_Import(t *testing.T) { + if ts.tableExists(t, dbschemaImport, "osm_all") != false { + t.Fatalf("table osm_all exists in schema %s", dbschemaImport) + } + ts.importOsm(t) + ts.deployOsm(t) + if ts.tableExists(t, dbschemaProduction, "osm_all") != true { + t.Fatalf("table osm_all does not exists in schema %s", dbschemaProduction) + } +} + +func TestAnyAny_InsertedNodes(t *testing.T) { + assertHstore(t, []checkElem{ + {"osm_all", 10000, "", nil}, // nodes without tags are not inserted + {"osm_all", 10001, "*", map[string]string{"random": "tag"}}, + {"osm_all", 10002, "*", map[string]string{"amenity": "shop"}}, + {"osm_all", 10003, "*", map[string]string{"random": "tag", "but": "mapped", "amenity": "shop"}}, + {"osm_amenities", 10002, "*", map[string]string{"amenity": "shop"}}, + {"osm_amenities", 10003, "*", map[string]string{"random": "tag", "but": "mapped", "amenity": "shop"}}, + }) +}