Skip to content

Commit b736701

Browse files
committed
Modernize geometries.lua example config
Move the "using-insert" variant over the old file which is not needed any more.
1 parent b010953 commit b736701

File tree

2 files changed

+59
-248
lines changed

2 files changed

+59
-248
lines changed

flex-config/geometries-using-insert.lua

Lines changed: 0 additions & 202 deletions
This file was deleted.

flex-config/geometries.lua

Lines changed: 59 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -11,25 +11,30 @@ tables.pois = osm2pgsql.define_node_table('pois', {
1111
{ column = 'tags', type = 'jsonb' },
1212
-- Create a geometry column for point geometries. The geometry will be
1313
-- in web mercator, EPSG 3857.
14-
{ column = 'geom', type = 'point' },
14+
--
15+
-- Usually we want to declare all geometry columns as "NOT NULL". If
16+
-- osm2pgsql encounters an invalid geometry (for whatever reason) it will
17+
-- generate a null geometry which will not be written to the database if
18+
-- "not_null" is set. The result is that broken geometries will just be
19+
-- silently ignored.
20+
{ column = 'geom', type = 'point', not_null = true },
1521
})
1622

1723
tables.ways = osm2pgsql.define_way_table('ways', {
1824
{ column = 'tags', type = 'jsonb' },
1925
-- Create a geometry column for linestring geometries. The geometry will
2026
-- be in latlong (WGS84), EPSG 4326.
21-
{ column = 'geom', type = 'linestring', projection = 4326 },
27+
{ column = 'geom', type = 'linestring', projection = 4326, not_null = true },
2228
})
2329

2430
tables.polygons = osm2pgsql.define_area_table('polygons', {
2531
{ column = 'tags', type = 'jsonb' },
26-
{ column = 'geom', type = 'geometry' },
27-
-- The 'area' type is used to store the calculated area of a polygon
28-
-- feature. This can be used in style sheets to only render larger polygons
29-
-- in small zoom levels. This will use the area in web mercator projection,
30-
-- you can set 'projection = 4326' to calculate the area in WGS84. Other
31-
-- projections are currently not supported.
32-
{ column = 'area', type = 'area' },
32+
-- If we don't set "not_null = true", we'll get NULL columns for invalid
33+
-- geometries. This can be useful if we want to detect those cases or
34+
-- if we have multiple geometry columns and some of them can be valid
35+
-- and others not.
36+
{ column = 'geom', type = 'geometry', projection = 4326 },
37+
{ column = 'area', type = 'real' },
3338
})
3439

3540
tables.boundaries = osm2pgsql.define_relation_table('boundaries', {
@@ -38,7 +43,7 @@ tables.boundaries = osm2pgsql.define_relation_table('boundaries', {
3843
-- Boundaries will be stitched together from relation members into long
3944
-- linestrings. This is a multilinestring column because sometimes the
4045
-- boundaries are not contiguous.
41-
{ column = 'geom', type = 'multilinestring' },
46+
{ column = 'geom', type = 'multilinestring', not_null = true },
4247
})
4348

4449
-- Tables don't have to have a geometry column. This one will only collect
@@ -101,15 +106,15 @@ function osm2pgsql.process_node(object)
101106
return
102107
end
103108

104-
-- The 'geom' column is not mentioned here. So the default geometry
105-
-- transformation for a column of type 'point' will be used and the
106-
-- node location will be written as Point geometry into the database.
107-
tables.pois:add_row({
108-
tags = object.tags
109+
local geom = object:as_point()
110+
111+
tables.pois:insert({
112+
tags = object.tags,
113+
geom = geom -- the point will be automatically be projected to 3857
109114
})
110115

111116
if object.tags.amenity == 'pub' then
112-
tables.pubs:add_row({
117+
tables.pubs:insert({
113118
name = object.tags.name
114119
})
115120
end
@@ -122,33 +127,36 @@ function osm2pgsql.process_way(object)
122127

123128
-- A closed way that also has the right tags for an area is a polygon.
124129
if object.is_closed and has_area_tags(object.tags) then
125-
tables.polygons:add_row({
130+
-- Creating the polygon geometry takes time, so we do it once here
131+
-- and later store it in the table and use it to calculate the area.
132+
local geom = object:as_polygon()
133+
tables.polygons:insert({
126134
tags = object.tags,
127-
-- The 'geom' column of the 'polygons' table is of type 'geometry'.
128-
-- There are several ways a way geometry could be converted to
129-
-- a geometry so you have to specify the geometry transformation.
130-
-- In this case we want to convert the way data to an area.
131-
geom = { create = 'area' }
135+
geom = geom,
136+
-- Calculate the area in Mercator projection and store in the
137+
-- area column
138+
area = geom:transform(3857):area()
132139
})
133140
else
134-
-- The 'geom' column of the 'ways' table is of type 'linestring'.
135-
-- Osm2pgsql knows how to create a linestring from a way, but
136-
-- if you want to specify extra parameters to this conversion,
137-
-- you have to do this explicitly. In this case we want to split
138-
-- long linestrings.
139-
--
140-
-- Set "split_at" to the maximum length the pieces should have. This
141-
-- length is in map units, so it depends on the projection used.
141+
-- We want to split long lines into smaller segments. We can use
142+
-- the "segmentize" function for that. The parameter specifies the
143+
-- maximum length the pieces should have. This length is in map units,
144+
-- so it depends on the projection used.
142145
-- "Traditional" osm2pgsql sets this to 1 for 4326 geometries and
143-
-- 100000 for 3857 (web mercator) geometries. The default is 0.0, which
144-
-- means no splitting.
146+
-- 100000 for 3857 (web mercator) geometries.
145147
--
146-
-- Note that if a way is split this will automatically create
147-
-- multiple rows that are identical except for the geometry.
148-
tables.ways:add_row({
149-
tags = object.tags,
150-
geom = { create = 'line', split_at = 1 }
151-
})
148+
-- Because the result of the segmentation is a multigeometry, we'll
149+
-- have to iterate over all the member geometries to be able to insert
150+
-- the data into a the 'geom' column of the 'ways' table which is of
151+
-- type 'linestring'. (We could have used a multilinestring geometry
152+
-- in our table instead.)
153+
local multi_geom = object:as_multilinestring():segmentize(1)
154+
for g in multi_geom:geometries() do
155+
tables.ways:insert({
156+
tags = object.tags,
157+
geom = g
158+
})
159+
end
152160
end
153161
end
154162

@@ -161,25 +169,30 @@ function osm2pgsql.process_relation(object)
161169

162170
-- Store boundary relations as multilinestrings
163171
if relation_type == 'boundary' then
164-
tables.boundaries:add_row({
172+
tables.boundaries:insert({
165173
type = object:grab_tag('boundary'),
166174
tags = object.tags,
167175
-- For relations there is no clear definition what their geometry
168-
-- is, so you have to declare the geometry transformation
169-
-- explicitly.
170-
geom = { create = 'line' }
176+
-- is, so you have to decide on the geometry transformation you
177+
-- want. In this case we want the boundary as multilinestring
178+
-- and we want lines merged as much as possible.
179+
geom = object:as_multilinestring():line_merge()
171180
})
172181
return
173182
end
174183

175184
-- Store multipolygon relations as polygons
176185
if relation_type == 'multipolygon' then
177-
tables.polygons:add_row({
186+
local geom = object:as_multipolygon()
187+
tables.polygons:insert({
178188
tags = object.tags,
179189
-- For relations there is no clear definition what their geometry
180-
-- is, so you have to declare the geometry transformation
181-
-- explicitly.
182-
geom = { create = 'area' }
190+
-- is, so you have to decide on the geometry transformation.
191+
-- In this case we know from the type tag its a (multi)polygon.
192+
geom = geom,
193+
-- Calculate the area in Mercator projection and store in the
194+
-- area column
195+
area = geom:transform(3857):area()
183196
})
184197
end
185198
end

0 commit comments

Comments
 (0)