Merge lp:~cwilson/spud/pythonnewkeywarning into lp:spud

Proposed by Cian Wilson
Status: Merged
Merged at revision: 539
Proposed branch: lp:~cwilson/spud/pythonnewkeywarning
Merge into: lp:spud
Diff against target: 113 lines (+29/-18)
2 files modified
python/libspud.c (+22/-18)
python/test_libspud.py (+7/-0)
To merge this branch: bzr merge lp:~cwilson/spud/pythonnewkeywarning
Reviewer Review Type Date Requested Status
Stephan Kramer Approve
Review via email: mp+318869@code.launchpad.net

Description of the change

This merge implements a fix for exception handling in set_option through the python interface- specifically handling SpudNewKeyWarnings.

Previously it would raise an exception but not return the right state (NULL) for it to be caught. Now SpudNewKeyWarning can be caught in python.

Additionally it was not possible to set a new option with type double through python. This appears to be because the PyArg_Parse function is broken (and its use discouraged in the documentation). Switching this to PyFloat_AS_DOUBLE, which works.

Modifying the python tests to reflect these changes.

Also tidying up messages associated with python exceptions.

To post a comment you must log in.
Revision history for this message
Stephan Kramer (s-kramer) wrote :

Looks glorious!

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'python/libspud.c'
2--- python/libspud.c 2012-07-17 20:14:59 +0000
3+++ python/libspud.c 2017-03-03 05:26:25 +0000
4@@ -22,44 +22,44 @@
5 char errormessage [MAXLENGTH];
6
7 if (outcome == SPUD_KEY_ERROR){
8- snprintf(errormessage, MAXLENGTH, "Error: The specified option is not present \
9- in the dictionary in %s", functionname);
10+ snprintf(errormessage, MAXLENGTH, "Error: The specified option is not present "
11+ "in the dictionary in %s", functionname);
12 PyErr_SetString(SpudKeyError, errormessage);
13 return NULL;
14 }
15 if (outcome == SPUD_TYPE_ERROR){
16- snprintf(errormessage, MAXLENGTH, "Error: The specified option has a different \
17- type from that of the option argument provided in %s", functionname);
18+ snprintf(errormessage, MAXLENGTH, "Error: The specified option has a different "
19+ "type from that of the option argument provided in (%s).", functionname);
20 PyErr_SetString(SpudTypeError, errormessage);
21 return NULL;
22 }
23 if (outcome == SPUD_NEW_KEY_WARNING){
24- snprintf(errormessage, MAXLENGTH, "Warning: The option being inserted is not ] \
25- already in the dictionary %s", functionname);
26+ snprintf(errormessage, MAXLENGTH, "Warning: The option being inserted is not "
27+ "already in the dictionary (%s).", functionname);
28 PyErr_SetString(SpudNewKeyWarning, errormessage);
29 return NULL;
30 }
31 if (outcome == SPUD_FILE_ERROR){
32- snprintf(errormessage, MAXLENGTH, "Error: The specified options file cannot be \
33- read or written to as the routine requires in %s", functionname);
34+ snprintf(errormessage, MAXLENGTH, "Error: The specified options file cannot be "
35+ "read or written to as the routine requires in (%s).", functionname);
36 PyErr_SetString(SpudFileError, errormessage);
37 return NULL;
38 }
39 if (outcome == SPUD_RANK_ERROR){
40- snprintf(errormessage, MAXLENGTH, "Error: The specified option has a different rank from \
41- that of the option argument provided %s", functionname);
42+ snprintf(errormessage, MAXLENGTH, "Error: The specified option has a different rank from "
43+ "that of the option argument provided (%s).", functionname);
44 PyErr_SetString(SpudRankError, errormessage);
45 return NULL;
46 }
47 if (outcome == SPUD_SHAPE_ERROR){
48- snprintf(errormessage, MAXLENGTH, "Error: The specified option has a different shape from \
49- that of the option argument provided in %s", functionname);
50+ snprintf(errormessage, MAXLENGTH, "Error: The specified option has a different shape from "
51+ "that of the option argument provided in (%s).", functionname);
52 PyErr_SetString(SpudShapeError, errormessage);
53 return NULL;
54 }
55 if (outcome == SPUD_ATTR_SET_FAILED_WARNING){
56- snprintf(errormessage, MAXLENGTH, "Warning: The option being set as an attribute can not be \
57- set as an attribute in %s", functionname);
58+ snprintf(errormessage, MAXLENGTH, "Warning: The option being set as an attribute can not be "
59+ "set as an attribute in (%s).", functionname);
60 PyErr_SetString(SpudAttrSetFailedWarning, errormessage);
61 return NULL;
62 }
63@@ -655,8 +655,7 @@
64 int outcomeSetOption = SPUD_NO_ERROR;
65
66 if (type == SPUD_DOUBLE){ //scalar is double
67- double val;
68- PyArg_Parse(pyscalar, "d", &val);
69+ double val = PyFloat_AS_DOUBLE(pyscalar);
70 outcomeSetOption = spud_set_option(key, key_len, &val, type, rank, shape);
71 }
72 else if (type == SPUD_INT){
73@@ -767,7 +766,12 @@
74 }
75 }
76
77- Py_RETURN_NONE;
78+ if (PyErr_Occurred()){
79+ return NULL;
80+ }
81+ else {
82+ Py_RETURN_NONE;
83+ }
84 }
85
86 static PyObject*
87@@ -836,7 +840,7 @@
88 SpudNewKeyWarning = PyErr_NewException("SpudNewKey.warning", NULL, NULL);
89 SpudKeyError = PyErr_NewException("SpudKey.error", NULL, NULL);
90 SpudTypeError = PyErr_NewException("SpudType.error", NULL, NULL);
91- SpudFileError = PyErr_NewException("SpudFile.warning", NULL, NULL);
92+ SpudFileError = PyErr_NewException("SpudFile.error", NULL, NULL);
93 SpudAttrSetFailedWarning = PyErr_NewException("SpudAttrSetFailed.warning", NULL, NULL);
94 SpudShapeError = PyErr_NewException("SpudShape.error", NULL, NULL);
95 SpudRankError = PyErr_NewException("SpudRank.error", NULL, NULL);
96
97=== modified file 'python/test_libspud.py'
98--- python/test_libspud.py 2011-11-04 13:55:59 +0000
99+++ python/test_libspud.py 2017-03-03 05:26:25 +0000
100@@ -87,6 +87,13 @@
101
102 libspud.write_options('test_out.flml')
103
104+try:
105+ libspud.set_option('/test', 4.3)
106+except libspud.SpudNewKeyWarning, e:
107+ pass
108+
109+assert libspud.get_option('/test') == 4.3
110+
111 libspud.set_option('/test',4)
112
113 assert libspud.get_option('/test') == 4

Subscribers

People subscribed via source and target branches