Skip to content

Commit 983d108

Browse files
committed
Use generic attribute management in PL/Python
Switch the implementation of the plan and result types to generic attribute management, as described at <http://docs.python.org/extending/newtypes.html>. This modernizes and simplifies the code a bit and prepares for Python 3.1, where the old way doesn't work anymore.
1 parent 5dff936 commit 983d108

File tree

3 files changed

+67
-28
lines changed

3 files changed

+67
-28
lines changed

src/pl/plpython/expected/plpython_spi.out

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -111,3 +111,24 @@ SELECT join_sequences(sequences) FROM sequences
111111
----------------
112112
(0 rows)
113113

114+
--
115+
-- plan and result objects
116+
--
117+
CREATE FUNCTION result_nrows_test() RETURNS int
118+
AS $$
119+
plan = plpy.prepare("SELECT 1 UNION SELECT 2")
120+
plpy.info(plan.status()) # not really documented or useful
121+
result = plpy.execute(plan)
122+
if result.status() > 0:
123+
return result.nrows()
124+
else:
125+
return None
126+
$$ LANGUAGE plpythonu;
127+
SELECT result_nrows_test();
128+
INFO: (True,)
129+
CONTEXT: PL/Python function "result_nrows_test"
130+
result_nrows_test
131+
-------------------
132+
2
133+
(1 row)
134+

src/pl/plpython/plpython.c

Lines changed: 28 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
/**********************************************************************
22
* plpython.c - python as a procedural language for PostgreSQL
33
*
4-
* $PostgreSQL: pgsql/src/pl/plpython/plpython.c,v 1.125 2009/08/14 13:12:21 petere Exp $
4+
* $PostgreSQL: pgsql/src/pl/plpython/plpython.c,v 1.126 2009/08/25 08:14:42 petere Exp $
55
*
66
*********************************************************************
77
*/
@@ -2050,12 +2050,10 @@ static PyObject *PLy_fatal(PyObject *, PyObject *);
20502050
#define is_PLyPlanObject(x) ((x)->ob_type == &PLy_PlanType)
20512051
static PyObject *PLy_plan_new(void);
20522052
static void PLy_plan_dealloc(PyObject *);
2053-
static PyObject *PLy_plan_getattr(PyObject *, char *);
20542053
static PyObject *PLy_plan_status(PyObject *, PyObject *);
20552054

20562055
static PyObject *PLy_result_new(void);
20572056
static void PLy_result_dealloc(PyObject *);
2058-
static PyObject *PLy_result_getattr(PyObject *, char *);
20592057
static PyObject *PLy_result_nrows(PyObject *, PyObject *);
20602058
static PyObject *PLy_result_status(PyObject *, PyObject *);
20612059
static Py_ssize_t PLy_result_length(PyObject *);
@@ -2072,6 +2070,11 @@ static PyObject *PLy_spi_execute_plan(PyObject *, PyObject *, long);
20722070
static PyObject *PLy_spi_execute_fetch_result(SPITupleTable *, int, int);
20732071

20742072

2073+
static PyMethodDef PLy_plan_methods[] = {
2074+
{"status", PLy_plan_status, METH_VARARGS, NULL},
2075+
{NULL, NULL, 0, NULL}
2076+
};
2077+
20752078
static PyTypeObject PLy_PlanType = {
20762079
PyObject_HEAD_INIT(NULL)
20772080
0, /* ob_size */
@@ -2084,7 +2087,7 @@ static PyTypeObject PLy_PlanType = {
20842087
*/
20852088
PLy_plan_dealloc, /* tp_dealloc */
20862089
0, /* tp_print */
2087-
PLy_plan_getattr, /* tp_getattr */
2090+
0, /* tp_getattr */
20882091
0, /* tp_setattr */
20892092
0, /* tp_compare */
20902093
0, /* tp_repr */
@@ -2099,11 +2102,13 @@ static PyTypeObject PLy_PlanType = {
20992102
0, /* tp_as_buffer */
21002103
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
21012104
PLy_plan_doc, /* tp_doc */
2102-
};
2103-
2104-
static PyMethodDef PLy_plan_methods[] = {
2105-
{"status", PLy_plan_status, METH_VARARGS, NULL},
2106-
{NULL, NULL, 0, NULL}
2105+
0, /* tp_traverse */
2106+
0, /* tp_clear */
2107+
0, /* tp_richcompare */
2108+
0, /* tp_weaklistoffset */
2109+
0, /* tp_iter */
2110+
0, /* tp_iternext */
2111+
PLy_plan_methods, /* tp_tpmethods */
21072112
};
21082113

21092114
static PySequenceMethods PLy_result_as_sequence = {
@@ -2116,6 +2121,12 @@ static PySequenceMethods PLy_result_as_sequence = {
21162121
PLy_result_ass_slice, /* sq_ass_slice */
21172122
};
21182123

2124+
static PyMethodDef PLy_result_methods[] = {
2125+
{"nrows", PLy_result_nrows, METH_VARARGS, NULL},
2126+
{"status", PLy_result_status, METH_VARARGS, NULL},
2127+
{NULL, NULL, 0, NULL}
2128+
};
2129+
21192130
static PyTypeObject PLy_ResultType = {
21202131
PyObject_HEAD_INIT(NULL)
21212132
0, /* ob_size */
@@ -2128,7 +2139,7 @@ static PyTypeObject PLy_ResultType = {
21282139
*/
21292140
PLy_result_dealloc, /* tp_dealloc */
21302141
0, /* tp_print */
2131-
PLy_result_getattr, /* tp_getattr */
2142+
0, /* tp_getattr */
21322143
0, /* tp_setattr */
21332144
0, /* tp_compare */
21342145
0, /* tp_repr */
@@ -2143,12 +2154,13 @@ static PyTypeObject PLy_ResultType = {
21432154
0, /* tp_as_buffer */
21442155
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
21452156
PLy_result_doc, /* tp_doc */
2146-
};
2147-
2148-
static PyMethodDef PLy_result_methods[] = {
2149-
{"nrows", PLy_result_nrows, METH_VARARGS, NULL},
2150-
{"status", PLy_result_status, METH_VARARGS, NULL},
2151-
{NULL, NULL, 0, NULL}
2157+
0, /* tp_traverse */
2158+
0, /* tp_clear */
2159+
0, /* tp_richcompare */
2160+
0, /* tp_weaklistoffset */
2161+
0, /* tp_iter */
2162+
0, /* tp_iternext */
2163+
PLy_result_methods, /* tp_tpmethods */
21522164
};
21532165

21542166
static PyMethodDef PLy_methods[] = {
@@ -2217,12 +2229,6 @@ PLy_plan_dealloc(PyObject *arg)
22172229
}
22182230

22192231

2220-
static PyObject *
2221-
PLy_plan_getattr(PyObject *self, char *name)
2222-
{
2223-
return Py_FindMethod(PLy_plan_methods, self, name);
2224-
}
2225-
22262232
static PyObject *
22272233
PLy_plan_status(PyObject *self, PyObject *args)
22282234
{
@@ -2270,12 +2276,6 @@ PLy_result_dealloc(PyObject *arg)
22702276
arg->ob_type->tp_free(arg);
22712277
}
22722278

2273-
static PyObject *
2274-
PLy_result_getattr(PyObject *self, char *name)
2275-
{
2276-
return Py_FindMethod(PLy_result_methods, self, name);
2277-
}
2278-
22792279
static PyObject *
22802280
PLy_result_nrows(PyObject *self, PyObject *args)
22812281
{

src/pl/plpython/sql/plpython_spi.sql

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -87,3 +87,21 @@ SELECT join_sequences(sequences) FROM sequences
8787
WHERE join_sequences(sequences) ~* '^A';
8888
SELECT join_sequences(sequences) FROM sequences
8989
WHERE join_sequences(sequences) ~* '^B';
90+
91+
92+
--
93+
-- plan and result objects
94+
--
95+
96+
CREATE FUNCTION result_nrows_test() RETURNS int
97+
AS $$
98+
plan = plpy.prepare("SELECT 1 UNION SELECT 2")
99+
plpy.info(plan.status()) # not really documented or useful
100+
result = plpy.execute(plan)
101+
if result.status() > 0:
102+
return result.nrows()
103+
else:
104+
return None
105+
$$ LANGUAGE plpythonu;
106+
107+
SELECT result_nrows_test();

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy