Skip to content

Commit 121f48d

Browse files
committed
[processing] add import into spatialite algorithm
1 parent 7a05a7a commit 121f48d

File tree

5 files changed

+157
-5
lines changed

5 files changed

+157
-5
lines changed

python/plugins/processing/algs/help/qgis.yaml

+3
Original file line numberDiff line numberDiff line change
@@ -198,6 +198,9 @@ qgis:hublines:
198198
qgis:hypsometriccurves: >
199199
This algorithm computes hypsometric curves for an input Digital Elevation Model. Curves are produced as table files in an output folder specified by the user.
200200

201+
qgis:importintospatialite: >
202+
This algorithms imports a vector layer into a Spatialite database, creating a new table.
203+
201204
qgis:importintopostgis: >
202205
This algorithms imports a vector layer into a PostGIS database, creating a new table.
203206

python/plugins/processing/algs/qgis/ImportIntoPostGIS.py

+5-3
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ def defineCharacteristics(self):
6565
self.addParameter(ParameterString(self.SCHEMA,
6666
self.tr('Schema (schema name)'), 'public'))
6767
self.addParameter(ParameterString(self.TABLENAME,
68-
self.tr('Table to import to (leave blank to use layer name)')))
68+
self.tr('Table to import to (leave blank to use layer name)'), optional=True))
6969
self.addParameter(ParameterTableField(self.PRIMARY_KEY,
7070
self.tr('Primary key field'), self.INPUT, optional=True))
7171
self.addParameter(ParameterString(self.GEOMETRY_COLUMN,
@@ -100,8 +100,10 @@ def processAlgorithm(self, progress):
100100
layerUri = self.getParameterValue(self.INPUT)
101101
layer = dataobjects.getObjectFromUri(layerUri)
102102

103-
table = self.getParameterValue(self.TABLENAME).strip()
104-
if table == '':
103+
table = self.getParameterValue(self.TABLENAME)
104+
if table:
105+
table.strip()
106+
if not table or table == '':
105107
table = layer.name()
106108
table = "_".join(table.split(".")[:-1])
107109
table = table.replace(' ', '').lower()[0:62]
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,137 @@
1+
# -*- coding: utf-8 -*-
2+
3+
"""
4+
***************************************************************************
5+
ImportIntoSpatialite.py
6+
---------------------
7+
Date : October 2016
8+
Copyright : (C) 2016 by Mathieu Pellerin
9+
Email : nirvn dot asia at gmail dot com
10+
***************************************************************************
11+
* *
12+
* This program is free software; you can redistribute it and/or modify *
13+
* it under the terms of the GNU General Public License as published by *
14+
* the Free Software Foundation; either version 2 of the License, or *
15+
* (at your option) any later version. *
16+
* *
17+
***************************************************************************
18+
"""
19+
20+
__author__ = 'Mathieu Pellerin'
21+
__date__ = 'October 2016'
22+
__copyright__ = '(C) 2012, Mathieu Pellerin'
23+
24+
# This will get replaced with a git SHA1 when you do a git archive
25+
26+
__revision__ = '$Format:%H$'
27+
28+
from qgis.PyQt.QtCore import QSettings
29+
from qgis.core import QgsDataSourceUri, QgsVectorLayerImport
30+
31+
from processing.core.GeoAlgorithm import GeoAlgorithm
32+
from processing.core.GeoAlgorithmExecutionException import GeoAlgorithmExecutionException
33+
from processing.core.parameters import ParameterBoolean
34+
from processing.core.parameters import ParameterVector
35+
from processing.core.parameters import ParameterString
36+
from processing.core.parameters import ParameterSelection
37+
from processing.core.parameters import ParameterTableField
38+
from processing.tools import dataobjects, spatialite
39+
40+
41+
class ImportIntoSpatialite(GeoAlgorithm):
42+
43+
DATABASE = 'DATABASE'
44+
TABLENAME = 'TABLENAME'
45+
INPUT = 'INPUT'
46+
OVERWRITE = 'OVERWRITE'
47+
CREATEINDEX = 'CREATEINDEX'
48+
GEOMETRY_COLUMN = 'GEOMETRY_COLUMN'
49+
LOWERCASE_NAMES = 'LOWERCASE_NAMES'
50+
DROP_STRING_LENGTH = 'DROP_STRING_LENGTH'
51+
FORCE_SINGLEPART = 'FORCE_SINGLEPART'
52+
PRIMARY_KEY = 'PRIMARY_KEY'
53+
ENCODING = 'ENCODING'
54+
55+
def defineCharacteristics(self):
56+
self.name, self.i18n_name = self.trAlgorithm('Import into Spatialite')
57+
self.group, self.i18n_group = self.trAlgorithm('Database')
58+
self.addParameter(ParameterVector(self.INPUT, self.tr('Layer to import')))
59+
self.addParameter(ParameterVector(self.DATABASE, self.tr('File database'), False, False))
60+
self.addParameter(ParameterString(self.TABLENAME, self.tr('Table to import to (leave blank to use layer name)'), optional=True))
61+
self.addParameter(ParameterTableField(self.PRIMARY_KEY, self.tr('Primary key field'), self.INPUT, optional=True))
62+
self.addParameter(ParameterString(self.GEOMETRY_COLUMN, self.tr('Geometry column'), 'geom'))
63+
self.addParameter(ParameterString(self.ENCODING, self.tr('Encoding'), 'UTF-8', optional=True))
64+
self.addParameter(ParameterBoolean(self.OVERWRITE, self.tr('Overwrite'), True))
65+
self.addParameter(ParameterBoolean(self.CREATEINDEX, self.tr('Create spatial index'), True))
66+
self.addParameter(ParameterBoolean(self.LOWERCASE_NAMES, self.tr('Convert field names to lowercase'), True))
67+
self.addParameter(ParameterBoolean(self.DROP_STRING_LENGTH, self.tr('Drop length constraints on character fields'), False))
68+
self.addParameter(ParameterBoolean(self.FORCE_SINGLEPART, self.tr('Create single-part geometries instead of multi-part'), False))
69+
70+
def processAlgorithm(self, progress):
71+
database = self.getParameterValue(self.DATABASE)
72+
uri = QgsDataSourceUri(database)
73+
if uri.database() is '':
74+
if '|layerid' in database:
75+
database = database[:database.find('|layerid')]
76+
uri = QgsDataSourceUri('dbname=\'%s\'' % (database))
77+
db = spatialite.GeoDB(uri)
78+
79+
overwrite = self.getParameterValue(self.OVERWRITE)
80+
createIndex = self.getParameterValue(self.CREATEINDEX)
81+
convertLowerCase = self.getParameterValue(self.LOWERCASE_NAMES)
82+
dropStringLength = self.getParameterValue(self.DROP_STRING_LENGTH)
83+
forceSinglePart = self.getParameterValue(self.FORCE_SINGLEPART)
84+
primaryKeyField = self.getParameterValue(self.PRIMARY_KEY) or 'id'
85+
encoding = self.getParameterValue(self.ENCODING)
86+
87+
layerUri = self.getParameterValue(self.INPUT)
88+
layer = dataobjects.getObjectFromUri(layerUri)
89+
90+
table = self.getParameterValue(self.TABLENAME)
91+
if table:
92+
table.strip()
93+
if not table or table == '':
94+
table = layer.name()
95+
table = table.replace(' ', '').lower()
96+
providerName = 'spatialite'
97+
98+
geomColumn = self.getParameterValue(self.GEOMETRY_COLUMN)
99+
if not geomColumn:
100+
geomColumn = 'the_geom'
101+
102+
options = {}
103+
if overwrite:
104+
options['overwrite'] = True
105+
if convertLowerCase:
106+
options['lowercaseFieldNames'] = True
107+
geomColumn = geomColumn.lower()
108+
if dropStringLength:
109+
options['dropStringConstraints'] = True
110+
if forceSinglePart:
111+
options['forceSinglePartGeometryType'] = True
112+
113+
# Clear geometry column for non-geometry tables
114+
if not layer.hasGeometryType():
115+
geomColumn = None
116+
117+
uri = db.uri
118+
uri.setDataSource('', table, geomColumn, '', primaryKeyField)
119+
120+
if encoding:
121+
layer.setProviderEncoding(encoding)
122+
123+
(ret, errMsg) = QgsVectorLayerImport.importLayer(
124+
layer,
125+
uri.uri(),
126+
providerName,
127+
self.crs,
128+
False,
129+
False,
130+
options,
131+
)
132+
if ret != 0:
133+
raise GeoAlgorithmExecutionException(
134+
self.tr('Error importing to Spatialite\n%s' % errMsg))
135+
136+
if geomColumn and createIndex:
137+
db.create_spatial_index(table, geomColumn)

python/plugins/processing/algs/qgis/QGISAlgorithmProvider.py

+2-1
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,7 @@
133133
from .PointsToPaths import PointsToPaths
134134
from .SpatialiteExecuteSQL import SpatialiteExecuteSQL
135135
from .PostGISExecuteSQL import PostGISExecuteSQL
136+
from .ImportIntoSpatialite import ImportIntoSpatialite
136137
from .ImportIntoPostGIS import ImportIntoPostGIS
137138
from .SetVectorStyle import SetVectorStyle
138139
from .SetRasterStyle import SetRasterStyle
@@ -214,7 +215,7 @@ def __init__(self):
214215
RandomPointsLayer(), RandomPointsPolygonsFixed(),
215216
RandomPointsPolygonsVariable(),
216217
RandomPointsAlongLines(), PointsToPaths(),
217-
SpatialiteExecuteSQL(),
218+
SpatialiteExecuteSQL(), ImportIntoSpatialite(),
218219
PostGISExecuteSQL(), ImportIntoPostGIS(),
219220
SetVectorStyle(), SetRasterStyle(),
220221
SelectByExpression(), HypsometricCurves(),

python/plugins/processing/tools/spatialite.py

+10-1
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@
2828
__revision__ = '$Format:%H$'
2929

3030
from qgis.utils import spatialite_connect
31-
3231
import sqlite3 as sqlite
3332

3433

@@ -124,3 +123,13 @@ def _exec_sql_and_commit(self, sql):
124123
except DbError:
125124
self.con.rollback()
126125
raise
126+
127+
def create_spatial_index(self, table, geom_column='the_geom'):
128+
sql = u"SELECT CreateSpatialIndex(%s, %s)" % (self._quote(table), self._quote(geom_column))
129+
self._exec_sql_and_commit(sql)
130+
131+
def _quote(self, identifier):
132+
"""Quote identifier."""
133+
134+
# quote identifier, and double the double-quotes
135+
return u"'%s'" % identifier.replace("'", "''")

0 commit comments

Comments
 (0)