LayerMapping 是一个数据导入实用程序

LayerMapping 类提供了一种将矢量空间数据文件(例如 shapefile)的内容映射到 GeoDjango 模型的方法。

这个实用程序是为了消除重复的代码,用于从矢量图层中提取几何和字段,将其转换为另一个坐标系统(例如 WGS84),然后插入到 GeoDjango 模型中而产生的。

Note

使用 LayerMapping 需要 GDAL。

Warning

GIS data sources, like shapefiles, may be very large. If you find that LayerMapping is using too much memory, set DEBUG to False in your settings. When DEBUG is set to True, Django automatically logs every SQL query -- and when SQL statements contain geometries, this may consume more memory than is typical.

例如

  1. 您需要一个受 GDAL 支持的数据源,比如一个 shapefile(这里我们使用一个简单的多边形 shapefile,名为 test_poly.shp,包含三个要素):

>>> from django.contrib.gis.gdal import DataSource
>>> ds = DataSource("test_poly.shp")
>>> layer = ds[0]
>>> print(layer.fields)  # Exploring the fields in the layer, we only want the 'str' field.
['float', 'int', 'str']
>>> print(len(layer))  # getting the number of features in the layer (should be 3)
3
>>> print(layer.geom_type)  # Should be 'Polygon'
Polygon
>>> print(layer.srs)  # WGS84 in WKT
GEOGCS["GCS_WGS_1984",
    DATUM["WGS_1984",
        SPHEROID["WGS_1984",6378137,298.257223563]],
    PRIMEM["Greenwich",0],
    UNIT["Degree",0.017453292519943295]]
  1. 现在我们定义相应的 Django 模型(确保使用 migrate):

    from django.contrib.gis.db import models
    
    
    class TestGeo(models.Model):
        name = models.CharField(max_length=25)  # corresponds to the 'str' field
        poly = models.PolygonField(srid=4269)  # we want our model in a different SRID
    
        def __str__(self):
            return "Name: %s" % self.name
    
  2. 使用 LayerMapping 提取所有要素并将它们放入数据库中:

>>> from django.contrib.gis.utils import LayerMapping
>>> from geoapp.models import TestGeo
>>> mapping = {
...     "name": "str",  # The 'name' model field maps to the 'str' layer field.
...     "poly": "POLYGON",  # For geometry fields use OGC name.
... }  # The mapping is a dictionary
>>> lm = LayerMapping(TestGeo, "test_poly.shp", mapping)
>>> lm.save(verbose=True)  # Save the layermap, imports the data.
Saved: Name: 1
Saved: Name: 2
Saved: Name: 3

Here, LayerMapping transformed the three geometries from the shapefile in their original spatial reference system (WGS84) to the spatial reference system of the GeoDjango model (NAD83). If no spatial reference system is defined for the layer, use the source_srs keyword with a SpatialReference object to specify one.

LayerMapping API

class LayerMapping(model, data_source, mapping, layer=0, source_srs=None, encoding=None, transaction_mode='commit_on_success', transform=True, unique=True, using='default')[source]

以下是在实例化 LayerMapping 对象期间可以使用的参数和关键字:

参数

描述

model

地理模型,不是 实例

data_source

The path to the OGR-supported data source file (e.g., a shapefile). Also accepts django.contrib.gis.gdal.DataSource instances.

mapping

一个字典:键是与模型字段对应的字符串,值对应于 OGR 要素的字符串字段名称,或者如果模型字段是地理字段,则应该对应于 OGR 几何类型,例如 'POINT''LINESTRING''POLYGON'

关键字参数

layer

要使用的数据源中的图层的索引(默认为0)。

source_srs

Use this to specify the source SRS manually (for example, some shapefiles don't come with a '.prj' file). An integer SRID, WKT or PROJ strings, and django.contrib.gis.gdal.SpatialReference objects are accepted.

encoding

Specifies the character set encoding of the strings in the OGR data source. For example, 'latin-1', 'utf-8', and 'cp437' are all valid encoding parameters.

transaction_mode

可以是 'commit_on_success' (默认)或 'autocommit'

transform

Setting this to False will disable coordinate transformations. In other words, geometries will be inserted into the database unmodified from their original state in the data source.

unique

Setting this to the name, or a tuple of names, from the given model will create models unique only to the given name(s). Geometries from each feature will be added into the collection associated with the unique model. Forces the transaction mode to be 'autocommit'.

using

在导入空间数据时设置要使用的数据库。默认为 'default'

save() 关键字参数

LayerMapping.save(verbose=False, fid_range=False, step=False, progress=False, silent=False, stream=sys.stdout, strict=False)[source]

The save() method also accepts keywords. These keywords are used for controlling output logging, error handling, and for importing specific feature ranges.

保存关键字参数

描述

fid_range

May be set with a slice or tuple of (begin, end) feature ID's to map from the data source. In other words, this keyword enables the user to selectively import a subset range of features in the geographic data source.

progress

When this keyword is set, status information will be printed giving the number of features processed and successfully saved. By default, progress information will be printed every 1000 features processed, however, this default may be overridden by setting this keyword with an integer for the desired interval.

silent

默认情况下,非致命错误通知将打印到 sys.stdout,但可以通过设置这个关键字来禁用这些通知。

step

如果设置为整数,事务将在每个步骤间隔之后发生。例如,如果 step=1000,则在第 1000 个要素、第 2000 个要素等之后会发生提交。

stream

Status information will be written to this file handle. Defaults to using sys.stdout, but any object with a write method is supported.

strict

Execution of the model mapping will cease upon the first error encountered. The default value (False) behavior is to attempt to continue.

verbose

如果设置,将在执行数据库上的每个模型保存后打印信息。

错误调试

内存耗尽

As noted in the warning at the top of this section, Django stores all SQL queries when DEBUG=True. Set DEBUG=False in your settings, and this should stop excessive memory use when running LayerMapping scripts.

MySQL: max_allowed_packet 错误

如果在使用 LayerMapping 和 MySQL 时遇到以下错误:

OperationalError: (1153, "Got a packet bigger than 'max_allowed_packet' bytes")

Then the solution is to increase the value of the max_allowed_packet setting in your MySQL configuration. For example, the default value may be something low like one megabyte -- the setting may be modified in MySQL's configuration file (my.cnf) in the [mysqld] section:

max_allowed_packet = 10M