OpenStreetMap — тайловый сервер

Есть такой ресурс под название OpenStreetMap. Смысл его в том, что его может наполнять любой пользователь интернета. А еще его могут использовать для разных задач, например для поиска какого-то адреса, для путешествий, использование в качестве «подложки» для картографов и т.д. и т.п.

И вот мне понадобилось его добавить в свой рабочий проект. Для этого есть 2 пути: использовать официальный сервис либо поднять свой сервер. Второй вариант может быть использован по ряду своих причин и какие были причины у меня останутся при мне.

Пример сгенерированного тайла

Подготовка

Для начала нужно определиться на чем это все разворачивать. В моем распоряжении есть сервер с мелкомягкими на 192ГБ ОЗУ и 8 ядрами процессора (16 потоков). Теперь подумаем как это все расположить.

Так как это сервер уже с какими-то ГИСами, то плодить еще кучу виртуалок не хочется. Попробуем все это уместить в более скромный набор «всего» и «вся».

На сервер уже есть PostgreSQL 14, хоть и не настроенный, а просто установленный (он нужен и для других ГИС-систем).

Судя по просмотру материала тайловый сервер все равно придется делать на Linux. Тогда понадобится виртуальная машина. Тут снова 2 вариант: создать виртуалку на сервере виртуализации (у нас в основной массе используется ProxMox) либо создать виртуалку на Hyper-V. Второй вариант тоже предпочтительней, так как весь абор будет находиться на одной железке. Создаем виртуалку и выделяем ей 8ГБ ОЗУ и 4 ядра ЦПУ. В качестве ОС накатываем Линух (у меня Debian 11). После установки не забываем настроить адреса и SSH.

Вальс в троем

Первым делом нужно установить PostGIS (без него вообще никак) на Windows-сервер. Это специально расширение для PostgreSQL. Загружаем, устанавливаем. После открываем pgAdmin4 (он должен входить в стандартную поставку с PostgreSQL for Windows) и создаем пользователя для БД (в моем случае «osm», задаем пароль и выставляем для него права «Can login». Далее создаем БД для работы (в моем случае опять же «osm») и в качестве владельца указываем ранее созданного пользователя. После для БД выполняем запросы со страницы https://postgis.net/install/, чтобы расширение PostGIS установилось для базы и еще одну команду:


CREATE EXTENSION hstore;

Расширение hstore нужно для хранения тэгов карты.

Сюда же нужно загрузить утилиту osm2pgsql.

Теперь переходим на виртуалку иустанавливаем целый ворох программ:


apt install mapnik lipapache2-mod-tile python-psycopg2 python2-yaml python3-yaml git npm nodejs fonts-noto-hinted fonts-noto-unhinted ttf-unifont fonts-noto-cjk fonts-hanazono libmapnik-dev mapnik-utils python3-mapnik

Далее понадобится пакет для генерации стиля тайлов карты:


npm -g i carto

После загружаем непосредственно стили:


git clone https://github.com/gravitystorm/openstreetmap-carto.git
cd openstreetmap-carto

Теперь открываем на редактирование файл project.mm, изменяем параметры подключения к БД в разделе osm2pgsql. В частности такие параметры как «dbname«,» host», «user» и «password». После выполняем команду:


carto project.mm > mapnik.xml

После подготовки необходимо скопировать файлы openstreet-carto.lua и openstreet-carto.style на Windows-сервер и положить их рядом с osm2pgsql.

Далее идем на сайт download.geofabrik.de, выбираем нужную карту и загружаем «.osm.pbf».

Пока выполняется загрузка карты можно сделать настройку PostgreSQL (если до этого еще не было настроено). Для этого берем PGTune (ищем в интернете), указываем необходимые параметры, вбиваем в утилиту и получаем параметры настрокий. Загоняем их в postgresql.conf. Эту операцию нужно делать только в случае ПЕРВОНАЧАЛЬНОЙ УСТАНОВКИ PostgreSQL. Вообще, по хорошему, есть специальные рекомендации настрокий. Все это прекрасно гуглится и яндексится.

После загрузки карты и не долго думая импортируем карту в БД:


osm2pgsql.exe -c -m -G --slim --hstore --tag-transform-script c:\maps\openstreet-carto.lua -d <имя БД> -H localhost -U <логин> -W -S c:\maps\openstreet-carto.style c:\maps\russia-latest.osm.pbf

Карта может импортироваться достаточно долго (в зависимости какая была выбрана). Возвращаемся на виртуалку и продолжаем настройку.

Здесь открываем /etc/renderd.conf и приводим примерно к следующему виду:


[renderd]
stats_file=/run/renderd/renderd.stats
socketname=/run/renderd/renderd.sock
num_threads=4
tile_dir=/var/cache/renderd/tiles
;tile_dir=/var/lib/mod_tile

[mapnik]
plugins_dir=/usr/lib/mapnik/3.1/input
font_dir=/usr/share/fonts/truetype
font_dir_recurse=true

[default]
XML=/root/openstreetmap-carto/mapnik.xml
URI=/tile/
TILESIZE=256
HOST=localhost
TILEDIR=/var/lib/mod_tile

По факту добавляем/правим раздел [default]. Так же при необходимости нужно поправить параметр num_threads. Директории /var/lib/mod_tile нету, по этому нужно создать и выдать соответствующие права доступа:


mkdir /var/lib/mod_tile
chown -R _renderd:_renderd

После в файле /etc/apache2/ports.conf правим порт с 80 на 8080 (ну или требуемый по вкусу). В заключении в /etc/apache2/sites-available создаем файл tileserver_site.conf:



    ServerAdmin         admin@osm.net

    #ServerName         osm.net
    DocumentRoot        /var/www/osm

    LogLevel info

    ModTileTileDir /var/lib/mod_tile
    LoadTileConfigFile /etc/renderd.conf
    ModTileRequestTimeout 30
    ModTileMissingRequestTimeout 60
    ModTileMaxLoadOld 2
    ModTileMaxLoadMissing 25
    ModTileRenderdSocketName /var/run/renderd/renderd.sock
    ModTileCacheDurationMax 604800
    ModTileCacheDurationDirty 900
    ModTileCacheDurationMinimum 10800
    ModTileCacheDurationMediumZoom 13 86400
    ModTileCacheDurationLowZoom 9 518400
    ModTileCacheLastModifiedFactor 0.20
    ModTileEnableTileThrottling Off
    ModTileEnableTileThrottlingXForward 0
    ModTileThrottlingTiles 10000 1 
    ModTileThrottlingRenders 128 0.2

    
        Options FollowSymLinks
        AllowOverride None
    
    
        Options -Indexes -FollowSymLinks -MultiViews
        AllowOverride None
        Order Allow,Deny
        Allow From All
    


Включаем конфиг:


/usr/sbin/a2ensite tileserver_site
systemctl restart apache2

После окончания импорта карты на том же web-сервере нужно выполнить некоторые скрипты. Для этого возвращаемся в директорию openstreetmap-carto и запускаем скрипт:


scripts/get-external-data.py -d <имя БД> -U <логин> -w <пароль> -H <адрес сервера БД>

Добавляем карты

Допустим, загрузили мы только один регион. Но а если хочется добавить еще один? Не проблема! Все тот же osm2pgsql с этим прекрасно справляется. Озадачиваем его следующим образом:


osm2pgsql.exe -a -m -G --slim --hstore --tag-transform-script c:\maps\openstreet-carto.lua -d <имя БД> -H localhost -U <логин> -W -S c:\maps\openstreet-carto.style f:\belarus-latest.osm.pbf

Ну и , собственно, ждем пока загрузится новый файл.

Хочу видеть результат

В общем то все готово, но хочется все это увидеть.

Для начала остановим renderd и запустим его в интеррактивном режиме (для отладки):


systemctl stop renderd
renderd -f -c /etc/renderd.conf

После можно открыть в браузере http://<ваш адрес>:8080/tile/0/0/0.png. В результате должен открыться тайл карты. Если нет, то смотрим консоль и логи web-сервера.

Но ведь хочется больше интеррактивности…

По пути /var/www/osm добавляем файл index.html со следующим содержимым:


<html lang="en">
  <head>
    <meta charset="utf-8">
    <link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/openlayers/openlayers.github.io@master/en/v6.14.1/css/ol.css" type="text/css">
    <style>
      .map {
        height: 400px;
        width: 100%;
      }
    </style>
    <script src="https://cdn.jsdelivr.net/gh/openlayers/openlayers.github.io@master/en/v6.14.1/build/ol.js"></script>
    <title>OpenLayers example</title>
  </head>
  <body>
    <h2>My Map</h2>
    <div id="map" class="map"></div>
    <script type="text/javascript">
      var map = new ol.Map({
        target: 'map',
        layers: [
          new ol.layer.Tile({
            source: new ol.source.XYZ({url: 'http://<ваш сервер>:8080/tile/{z}/{x}/{y}.png'})
          })
        ],
        view: new ol.View({
          center: ol.proj.fromLonLat([37.41, 8.82]),
          zoom: 4
        })
      });
    </script>
  </body>
</html>

И открываем http://<Ваш сервер>:8080. Должна появиться карта. Если нет, то проверяем ошибки.

Подводный камень

В моем случае была крайне низкая скорость. Причина этому были настройки сети в Hyper-V. Не известно по каким причинам, но виртуальный сетевой адаптер работал через мост и СУБД крайне медленно передавала данные. Коллега подсказал, что нужно избавиться от моста, после чего сеть начала работать так как нужно.

Немного оптимизации

В статье OSM User:Species/PostGIS Tuning описаны дополнительные индексы, которые могут помочь оптимизировать производительность базы. Здесь я их приводить не буду, так как в ней все очень хорошо расписано и в комментариях не нуждается.

Поделиться
Вы можете оставить комментарий, или ссылку на Ваш сайт.
Have seksuelle pr?stationer v?ret umulige pa grund af tilladelser til sex. Erektil dysfunktion omkring din Prov denne penis. Blodstrommen er fed, og der henvises ikke kun til

Оставить комментарий

Вы должны быть авторизованы, чтобы разместить комментарий.