Skip to content

Commit 42d5b9b

Browse files
committedAug 16, 2015
Python exceptions for invalid keys in QgsFields methods (fix #13221)
1 parent e800419 commit 42d5b9b

File tree

3 files changed

+160
-4
lines changed

3 files changed

+160
-4
lines changed
 

‎python/core/qgsfield.sip

Lines changed: 75 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -215,6 +215,18 @@ class QgsFields
215215
bool appendExpressionField( const QgsField& field, int originIndex );
216216
//! Remove a field with the given index
217217
void remove( int fieldIdx );
218+
%MethodCode
219+
if ( a0 < 0 || a0 >= sipCpp->count() )
220+
{
221+
PyErr_SetString(PyExc_KeyError, QByteArray::number(a0));
222+
sipIsErr = 1;
223+
}
224+
else
225+
{
226+
sipCpp->remove( a0 );
227+
}
228+
%End
229+
218230
//! Extend with fields from another QgsFields container
219231
void extend( const QgsFields& other );
220232

@@ -244,19 +256,78 @@ class QgsFields
244256
sipIsErr = 1;
245257
else
246258
sipRes = new QgsField(sipCpp->operator[](idx));
247-
248259
%End
260+
249261
//! Get field at particular index (must be in range 0..N-1)
250-
const QgsField& at( int i ) const;
262+
const QgsField& at( int i ) const /Factory/;
263+
%MethodCode
264+
if ( a0 < 0 || a0 >= sipCpp->count() )
265+
{
266+
PyErr_SetString(PyExc_KeyError, QByteArray::number(a0));
267+
sipIsErr = 1;
268+
}
269+
else
270+
{
271+
sipRes = new QgsField( sipCpp->at( a0 ) );
272+
}
273+
%End
274+
251275
//! Get field at particular index (must be in range 0..N-1)
252-
const QgsField& field( int fieldIdx ) const;
276+
const QgsField& field( int fieldIdx ) const /Factory/;
277+
%MethodCode
278+
if ( a0 < 0 || a0 >= sipCpp->count() )
279+
{
280+
PyErr_SetString(PyExc_KeyError, QByteArray::number(a0));
281+
sipIsErr = 1;
282+
}
283+
else
284+
{
285+
sipRes = new QgsField( sipCpp->field( a0 ) );
286+
}
287+
%End
288+
253289
//! Get field at particular index (must be in range 0..N-1)
254-
const QgsField& field( const QString& name ) const;
290+
const QgsField& field( const QString& name ) const /Factory/;
291+
%MethodCode
292+
int fieldIdx = sipCpp->indexFromName(*a0);
293+
if (fieldIdx == -1)
294+
{
295+
PyErr_SetString(PyExc_KeyError, a0->toAscii());
296+
sipIsErr = 1;
297+
}
298+
else
299+
{
300+
sipRes = new QgsField( sipCpp->field( *a0 ) );
301+
}
302+
%End
255303

256304
//! Get field's origin (value from an enumeration)
257305
FieldOrigin fieldOrigin( int fieldIdx ) const;
306+
%MethodCode
307+
if ( a0 < 0 || a0 >= sipCpp->count() )
308+
{
309+
PyErr_SetString(PyExc_KeyError, QByteArray::number(a0));
310+
sipIsErr = 1;
311+
}
312+
else
313+
{
314+
sipRes = sipCpp->fieldOrigin( a0 );
315+
}
316+
%End
317+
258318
//! Get field's origin index (its meaning is specific to each type of origin)
259319
int fieldOriginIndex( int fieldIdx ) const;
320+
%MethodCode
321+
if ( a0 < 0 || a0 >= sipCpp->count() )
322+
{
323+
PyErr_SetString(PyExc_KeyError, QByteArray::number(a0));
324+
sipIsErr = 1;
325+
}
326+
else
327+
{
328+
sipRes = sipCpp->fieldOriginIndex( a0 );
329+
}
330+
%End
260331

261332
//! Look up field's index from name. Returns -1 on error
262333
int indexFromName( const QString& name ) const;

‎tests/src/python/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@ ADD_PYTHON_TEST(PyQgsShapefileProvider test_provider_shapefile.py)
5353
ADD_PYTHON_TEST(PyQgsMemoryProvider test_provider_memory.py)
5454
ADD_PYTHON_TEST(PyQgsVectorColorRamp test_qgsvectorcolorramp.py)
5555
ADD_PYTHON_TEST(PyQgsSyntacticSugar test_syntactic_sugar.py)
56+
ADD_PYTHON_TEST(PyQgsField test_qgsfield.py)
5657

5758
IF (NOT WIN32)
5859
ADD_PYTHON_TEST(PyQgsLogger test_qgslogger.py)

‎tests/src/python/test_qgsfield.py

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
# -*- coding: utf-8 -*-
2+
"""QGIS Unit tests for QgsField.
3+
4+
.. note:: This program is free software; you can redistribute it and/or modify
5+
it under the terms of the GNU General Public License as published by
6+
the Free Software Foundation; either version 2 of the License, or
7+
(at your option) any later version.
8+
"""
9+
__author__ = 'Nyall Dawson'
10+
__date__ = '16/08/2015'
11+
__copyright__ = 'Copyright 2015, The QGIS Project'
12+
# This will get replaced with a git SHA1 when you do a git archive
13+
__revision__ = '$Format:%H$'
14+
15+
import qgis
16+
import os
17+
18+
from qgis.core import QgsField, QgsVectorLayer, NULL
19+
from utilities import (unitTestDataPath,
20+
getQgisTestApp,
21+
TestCase,
22+
unittest
23+
)
24+
from unittest import expectedFailure
25+
26+
QGISAPP, CANVAS, IFACE, PARENT = getQgisTestApp()
27+
28+
class TestQgsFields(TestCase):
29+
30+
def test_expections(self):
31+
ml=QgsVectorLayer("Point?crs=epsg:4236&field=id:integer&field=value:double",
32+
"test_data", "memory")
33+
assert ml.isValid()
34+
fields=ml.fields()
35+
36+
#check no error
37+
fields.remove(1)
38+
#check exceptions raised
39+
with self.assertRaises(KeyError):
40+
fields.remove(-1)
41+
with self.assertRaises(KeyError):
42+
fields.remove(111)
43+
44+
fields=ml.fields()
45+
#check no error
46+
fields.at(1)
47+
#check exceptions raised
48+
with self.assertRaises(KeyError):
49+
fields.at(-1)
50+
with self.assertRaises(KeyError):
51+
fields.at(111)
52+
53+
#check no error
54+
fields.field(1)
55+
#check exceptions raised
56+
with self.assertRaises(KeyError):
57+
fields.field(-1)
58+
with self.assertRaises(KeyError):
59+
fields.field(111)
60+
61+
#check no error
62+
fields.field('value')
63+
#check exceptions raised
64+
with self.assertRaises(KeyError):
65+
fields.field('bad')
66+
67+
#check no error
68+
fields.fieldOrigin(1)
69+
#check exceptions raised
70+
with self.assertRaises(KeyError):
71+
fields.fieldOrigin(-1)
72+
with self.assertRaises(KeyError):
73+
fields.fieldOrigin(111)
74+
75+
#check no error
76+
fields.fieldOriginIndex(1)
77+
#check exceptions raised
78+
with self.assertRaises(KeyError):
79+
fields.fieldOriginIndex(-1)
80+
with self.assertRaises(KeyError):
81+
fields.fieldOriginIndex(111)
82+
83+
if __name__ == '__main__':
84+
unittest.main()

0 commit comments

Comments
 (0)
Please sign in to comment.