]> granicus.if.org Git - postgresql/blob - src/pl/plpython/expected/plpython_types_3.out
PL/Python: Convert numeric to Decimal
[postgresql] / src / pl / plpython / expected / plpython_types_3.out
1 --
2 -- Test data type behavior
3 --
4 --
5 -- Base/common types
6 --
7 CREATE FUNCTION test_type_conversion_bool(x bool) RETURNS bool AS $$
8 plpy.info(x, type(x))
9 return x
10 $$ LANGUAGE plpython3u;
11 SELECT * FROM test_type_conversion_bool(true);
12 INFO:  (True, <class 'bool'>)
13 CONTEXT:  PL/Python function "test_type_conversion_bool"
14  test_type_conversion_bool 
15 ---------------------------
16  t
17 (1 row)
18
19 SELECT * FROM test_type_conversion_bool(false);
20 INFO:  (False, <class 'bool'>)
21 CONTEXT:  PL/Python function "test_type_conversion_bool"
22  test_type_conversion_bool 
23 ---------------------------
24  f
25 (1 row)
26
27 SELECT * FROM test_type_conversion_bool(null);
28 INFO:  (None, <class 'NoneType'>)
29 CONTEXT:  PL/Python function "test_type_conversion_bool"
30  test_type_conversion_bool 
31 ---------------------------
32  
33 (1 row)
34
35 -- test various other ways to express Booleans in Python
36 CREATE FUNCTION test_type_conversion_bool_other(n int) RETURNS bool AS $$
37 # numbers
38 if n == 0:
39    ret = 0
40 elif n == 1:
41    ret = 5
42 # strings
43 elif n == 2:
44    ret = ''
45 elif n == 3:
46    ret = 'fa' # true in Python, false in PostgreSQL
47 # containers
48 elif n == 4:
49    ret = []
50 elif n == 5:
51    ret = [0]
52 plpy.info(ret, not not ret)
53 return ret
54 $$ LANGUAGE plpython3u;
55 SELECT * FROM test_type_conversion_bool_other(0);
56 INFO:  (0, False)
57 CONTEXT:  PL/Python function "test_type_conversion_bool_other"
58  test_type_conversion_bool_other 
59 ---------------------------------
60  f
61 (1 row)
62
63 SELECT * FROM test_type_conversion_bool_other(1);
64 INFO:  (5, True)
65 CONTEXT:  PL/Python function "test_type_conversion_bool_other"
66  test_type_conversion_bool_other 
67 ---------------------------------
68  t
69 (1 row)
70
71 SELECT * FROM test_type_conversion_bool_other(2);
72 INFO:  ('', False)
73 CONTEXT:  PL/Python function "test_type_conversion_bool_other"
74  test_type_conversion_bool_other 
75 ---------------------------------
76  f
77 (1 row)
78
79 SELECT * FROM test_type_conversion_bool_other(3);
80 INFO:  ('fa', True)
81 CONTEXT:  PL/Python function "test_type_conversion_bool_other"
82  test_type_conversion_bool_other 
83 ---------------------------------
84  t
85 (1 row)
86
87 SELECT * FROM test_type_conversion_bool_other(4);
88 INFO:  ([], False)
89 CONTEXT:  PL/Python function "test_type_conversion_bool_other"
90  test_type_conversion_bool_other 
91 ---------------------------------
92  f
93 (1 row)
94
95 SELECT * FROM test_type_conversion_bool_other(5);
96 INFO:  ([0], True)
97 CONTEXT:  PL/Python function "test_type_conversion_bool_other"
98  test_type_conversion_bool_other 
99 ---------------------------------
100  t
101 (1 row)
102
103 CREATE FUNCTION test_type_conversion_char(x char) RETURNS char AS $$
104 plpy.info(x, type(x))
105 return x
106 $$ LANGUAGE plpython3u;
107 SELECT * FROM test_type_conversion_char('a');
108 INFO:  ('a', <class 'str'>)
109 CONTEXT:  PL/Python function "test_type_conversion_char"
110  test_type_conversion_char 
111 ---------------------------
112  a
113 (1 row)
114
115 SELECT * FROM test_type_conversion_char(null);
116 INFO:  (None, <class 'NoneType'>)
117 CONTEXT:  PL/Python function "test_type_conversion_char"
118  test_type_conversion_char 
119 ---------------------------
120  
121 (1 row)
122
123 CREATE FUNCTION test_type_conversion_int2(x int2) RETURNS int2 AS $$
124 plpy.info(x, type(x))
125 return x
126 $$ LANGUAGE plpython3u;
127 SELECT * FROM test_type_conversion_int2(100::int2);
128 INFO:  (100, <class 'int'>)
129 CONTEXT:  PL/Python function "test_type_conversion_int2"
130  test_type_conversion_int2 
131 ---------------------------
132                        100
133 (1 row)
134
135 SELECT * FROM test_type_conversion_int2(-100::int2);
136 INFO:  (-100, <class 'int'>)
137 CONTEXT:  PL/Python function "test_type_conversion_int2"
138  test_type_conversion_int2 
139 ---------------------------
140                       -100
141 (1 row)
142
143 SELECT * FROM test_type_conversion_int2(null);
144 INFO:  (None, <class 'NoneType'>)
145 CONTEXT:  PL/Python function "test_type_conversion_int2"
146  test_type_conversion_int2 
147 ---------------------------
148                           
149 (1 row)
150
151 CREATE FUNCTION test_type_conversion_int4(x int4) RETURNS int4 AS $$
152 plpy.info(x, type(x))
153 return x
154 $$ LANGUAGE plpython3u;
155 SELECT * FROM test_type_conversion_int4(100);
156 INFO:  (100, <class 'int'>)
157 CONTEXT:  PL/Python function "test_type_conversion_int4"
158  test_type_conversion_int4 
159 ---------------------------
160                        100
161 (1 row)
162
163 SELECT * FROM test_type_conversion_int4(-100);
164 INFO:  (-100, <class 'int'>)
165 CONTEXT:  PL/Python function "test_type_conversion_int4"
166  test_type_conversion_int4 
167 ---------------------------
168                       -100
169 (1 row)
170
171 SELECT * FROM test_type_conversion_int4(null);
172 INFO:  (None, <class 'NoneType'>)
173 CONTEXT:  PL/Python function "test_type_conversion_int4"
174  test_type_conversion_int4 
175 ---------------------------
176                           
177 (1 row)
178
179 CREATE FUNCTION test_type_conversion_int8(x int8) RETURNS int8 AS $$
180 plpy.info(x, type(x))
181 return x
182 $$ LANGUAGE plpython3u;
183 SELECT * FROM test_type_conversion_int8(100);
184 INFO:  (100, <class 'int'>)
185 CONTEXT:  PL/Python function "test_type_conversion_int8"
186  test_type_conversion_int8 
187 ---------------------------
188                        100
189 (1 row)
190
191 SELECT * FROM test_type_conversion_int8(-100);
192 INFO:  (-100, <class 'int'>)
193 CONTEXT:  PL/Python function "test_type_conversion_int8"
194  test_type_conversion_int8 
195 ---------------------------
196                       -100
197 (1 row)
198
199 SELECT * FROM test_type_conversion_int8(5000000000);
200 INFO:  (5000000000, <class 'int'>)
201 CONTEXT:  PL/Python function "test_type_conversion_int8"
202  test_type_conversion_int8 
203 ---------------------------
204                 5000000000
205 (1 row)
206
207 SELECT * FROM test_type_conversion_int8(null);
208 INFO:  (None, <class 'NoneType'>)
209 CONTEXT:  PL/Python function "test_type_conversion_int8"
210  test_type_conversion_int8 
211 ---------------------------
212                           
213 (1 row)
214
215 CREATE FUNCTION test_type_conversion_numeric(x numeric) RETURNS numeric AS $$
216 # print just the class name, not the type, to avoid differences
217 # between decimal and cdecimal
218 plpy.info(x, x.__class__.__name__)
219 return x
220 $$ LANGUAGE plpython3u;
221 SELECT * FROM test_type_conversion_numeric(100);
222 INFO:  (Decimal('100'), 'Decimal')
223 CONTEXT:  PL/Python function "test_type_conversion_numeric"
224  test_type_conversion_numeric 
225 ------------------------------
226                           100
227 (1 row)
228
229 SELECT * FROM test_type_conversion_numeric(-100);
230 INFO:  (Decimal('-100'), 'Decimal')
231 CONTEXT:  PL/Python function "test_type_conversion_numeric"
232  test_type_conversion_numeric 
233 ------------------------------
234                          -100
235 (1 row)
236
237 SELECT * FROM test_type_conversion_numeric(100.0);
238 INFO:  (Decimal('100.0'), 'Decimal')
239 CONTEXT:  PL/Python function "test_type_conversion_numeric"
240  test_type_conversion_numeric 
241 ------------------------------
242                         100.0
243 (1 row)
244
245 SELECT * FROM test_type_conversion_numeric(100.00);
246 INFO:  (Decimal('100.00'), 'Decimal')
247 CONTEXT:  PL/Python function "test_type_conversion_numeric"
248  test_type_conversion_numeric 
249 ------------------------------
250                        100.00
251 (1 row)
252
253 SELECT * FROM test_type_conversion_numeric(5000000000.5);
254 INFO:  (Decimal('5000000000.5'), 'Decimal')
255 CONTEXT:  PL/Python function "test_type_conversion_numeric"
256  test_type_conversion_numeric 
257 ------------------------------
258                  5000000000.5
259 (1 row)
260
261 SELECT * FROM test_type_conversion_numeric(1234567890.0987654321);
262 INFO:  (Decimal('1234567890.0987654321'), 'Decimal')
263 CONTEXT:  PL/Python function "test_type_conversion_numeric"
264  test_type_conversion_numeric 
265 ------------------------------
266         1234567890.0987654321
267 (1 row)
268
269 SELECT * FROM test_type_conversion_numeric(-1234567890.0987654321);
270 INFO:  (Decimal('-1234567890.0987654321'), 'Decimal')
271 CONTEXT:  PL/Python function "test_type_conversion_numeric"
272  test_type_conversion_numeric 
273 ------------------------------
274        -1234567890.0987654321
275 (1 row)
276
277 SELECT * FROM test_type_conversion_numeric(null);
278 INFO:  (None, 'NoneType')
279 CONTEXT:  PL/Python function "test_type_conversion_numeric"
280  test_type_conversion_numeric 
281 ------------------------------
282                              
283 (1 row)
284
285 CREATE FUNCTION test_type_conversion_float4(x float4) RETURNS float4 AS $$
286 plpy.info(x, type(x))
287 return x
288 $$ LANGUAGE plpython3u;
289 SELECT * FROM test_type_conversion_float4(100);
290 INFO:  (100.0, <class 'float'>)
291 CONTEXT:  PL/Python function "test_type_conversion_float4"
292  test_type_conversion_float4 
293 -----------------------------
294                          100
295 (1 row)
296
297 SELECT * FROM test_type_conversion_float4(-100);
298 INFO:  (-100.0, <class 'float'>)
299 CONTEXT:  PL/Python function "test_type_conversion_float4"
300  test_type_conversion_float4 
301 -----------------------------
302                         -100
303 (1 row)
304
305 SELECT * FROM test_type_conversion_float4(5000.5);
306 INFO:  (5000.5, <class 'float'>)
307 CONTEXT:  PL/Python function "test_type_conversion_float4"
308  test_type_conversion_float4 
309 -----------------------------
310                       5000.5
311 (1 row)
312
313 SELECT * FROM test_type_conversion_float4(null);
314 INFO:  (None, <class 'NoneType'>)
315 CONTEXT:  PL/Python function "test_type_conversion_float4"
316  test_type_conversion_float4 
317 -----------------------------
318                             
319 (1 row)
320
321 CREATE FUNCTION test_type_conversion_float8(x float8) RETURNS float8 AS $$
322 plpy.info(x, type(x))
323 return x
324 $$ LANGUAGE plpython3u;
325 SELECT * FROM test_type_conversion_float8(100);
326 INFO:  (100.0, <class 'float'>)
327 CONTEXT:  PL/Python function "test_type_conversion_float8"
328  test_type_conversion_float8 
329 -----------------------------
330                          100
331 (1 row)
332
333 SELECT * FROM test_type_conversion_float8(-100);
334 INFO:  (-100.0, <class 'float'>)
335 CONTEXT:  PL/Python function "test_type_conversion_float8"
336  test_type_conversion_float8 
337 -----------------------------
338                         -100
339 (1 row)
340
341 SELECT * FROM test_type_conversion_float8(5000000000.5);
342 INFO:  (5000000000.5, <class 'float'>)
343 CONTEXT:  PL/Python function "test_type_conversion_float8"
344  test_type_conversion_float8 
345 -----------------------------
346                 5000000000.5
347 (1 row)
348
349 SELECT * FROM test_type_conversion_float8(null);
350 INFO:  (None, <class 'NoneType'>)
351 CONTEXT:  PL/Python function "test_type_conversion_float8"
352  test_type_conversion_float8 
353 -----------------------------
354                             
355 (1 row)
356
357 CREATE FUNCTION test_type_conversion_oid(x oid) RETURNS oid AS $$
358 plpy.info(x, type(x))
359 return x
360 $$ LANGUAGE plpython3u;
361 SELECT * FROM test_type_conversion_oid(100);
362 INFO:  (100, <class 'int'>)
363 CONTEXT:  PL/Python function "test_type_conversion_oid"
364  test_type_conversion_oid 
365 --------------------------
366                       100
367 (1 row)
368
369 SELECT * FROM test_type_conversion_oid(2147483649);
370 INFO:  (2147483649, <class 'int'>)
371 CONTEXT:  PL/Python function "test_type_conversion_oid"
372  test_type_conversion_oid 
373 --------------------------
374                2147483649
375 (1 row)
376
377 SELECT * FROM test_type_conversion_oid(null);
378 INFO:  (None, <class 'NoneType'>)
379 CONTEXT:  PL/Python function "test_type_conversion_oid"
380  test_type_conversion_oid 
381 --------------------------
382                          
383 (1 row)
384
385 CREATE FUNCTION test_type_conversion_text(x text) RETURNS text AS $$
386 plpy.info(x, type(x))
387 return x
388 $$ LANGUAGE plpython3u;
389 SELECT * FROM test_type_conversion_text('hello world');
390 INFO:  ('hello world', <class 'str'>)
391 CONTEXT:  PL/Python function "test_type_conversion_text"
392  test_type_conversion_text 
393 ---------------------------
394  hello world
395 (1 row)
396
397 SELECT * FROM test_type_conversion_text(null);
398 INFO:  (None, <class 'NoneType'>)
399 CONTEXT:  PL/Python function "test_type_conversion_text"
400  test_type_conversion_text 
401 ---------------------------
402  
403 (1 row)
404
405 CREATE FUNCTION test_type_conversion_bytea(x bytea) RETURNS bytea AS $$
406 plpy.info(x, type(x))
407 return x
408 $$ LANGUAGE plpython3u;
409 SELECT * FROM test_type_conversion_bytea('hello world');
410 INFO:  (b'hello world', <class 'bytes'>)
411 CONTEXT:  PL/Python function "test_type_conversion_bytea"
412  test_type_conversion_bytea 
413 ----------------------------
414  \x68656c6c6f20776f726c64
415 (1 row)
416
417 SELECT * FROM test_type_conversion_bytea(E'null\\000byte');
418 INFO:  (b'null\x00byte', <class 'bytes'>)
419 CONTEXT:  PL/Python function "test_type_conversion_bytea"
420  test_type_conversion_bytea 
421 ----------------------------
422  \x6e756c6c0062797465
423 (1 row)
424
425 SELECT * FROM test_type_conversion_bytea(null);
426 INFO:  (None, <class 'NoneType'>)
427 CONTEXT:  PL/Python function "test_type_conversion_bytea"
428  test_type_conversion_bytea 
429 ----------------------------
430  
431 (1 row)
432
433 CREATE FUNCTION test_type_marshal() RETURNS bytea AS $$
434 import marshal
435 return marshal.dumps('hello world')
436 $$ LANGUAGE plpython3u;
437 CREATE FUNCTION test_type_unmarshal(x bytea) RETURNS text AS $$
438 import marshal
439 try:
440     return marshal.loads(x)
441 except ValueError as e:
442     return 'FAILED: ' + str(e)
443 $$ LANGUAGE plpython3u;
444 SELECT test_type_unmarshal(x) FROM test_type_marshal() x;
445  test_type_unmarshal 
446 ---------------------
447  hello world
448 (1 row)
449
450 --
451 -- Domains
452 --
453 CREATE DOMAIN booltrue AS bool CHECK (VALUE IS TRUE OR VALUE IS NULL);
454 CREATE FUNCTION test_type_conversion_booltrue(x booltrue, y bool) RETURNS booltrue AS $$
455 return y
456 $$ LANGUAGE plpython3u;
457 SELECT * FROM test_type_conversion_booltrue(true, true);
458  test_type_conversion_booltrue 
459 -------------------------------
460  t
461 (1 row)
462
463 SELECT * FROM test_type_conversion_booltrue(false, true);
464 ERROR:  value for domain booltrue violates check constraint "booltrue_check"
465 SELECT * FROM test_type_conversion_booltrue(true, false);
466 ERROR:  value for domain booltrue violates check constraint "booltrue_check"
467 CONTEXT:  while creating return value
468 PL/Python function "test_type_conversion_booltrue"
469 CREATE DOMAIN uint2 AS int2 CHECK (VALUE >= 0);
470 CREATE FUNCTION test_type_conversion_uint2(x uint2, y int) RETURNS uint2 AS $$
471 plpy.info(x, type(x))
472 return y
473 $$ LANGUAGE plpython3u;
474 SELECT * FROM test_type_conversion_uint2(100::uint2, 50);
475 INFO:  (100, <class 'int'>)
476 CONTEXT:  PL/Python function "test_type_conversion_uint2"
477  test_type_conversion_uint2 
478 ----------------------------
479                          50
480 (1 row)
481
482 SELECT * FROM test_type_conversion_uint2(100::uint2, -50);
483 INFO:  (100, <class 'int'>)
484 CONTEXT:  PL/Python function "test_type_conversion_uint2"
485 ERROR:  value for domain uint2 violates check constraint "uint2_check"
486 CONTEXT:  while creating return value
487 PL/Python function "test_type_conversion_uint2"
488 SELECT * FROM test_type_conversion_uint2(null, 1);
489 INFO:  (None, <class 'NoneType'>)
490 CONTEXT:  PL/Python function "test_type_conversion_uint2"
491  test_type_conversion_uint2 
492 ----------------------------
493                           1
494 (1 row)
495
496 CREATE DOMAIN nnint AS int CHECK (VALUE IS NOT NULL);
497 CREATE FUNCTION test_type_conversion_nnint(x nnint, y int) RETURNS nnint AS $$
498 return y
499 $$ LANGUAGE plpython3u;
500 SELECT * FROM test_type_conversion_nnint(10, 20);
501  test_type_conversion_nnint 
502 ----------------------------
503                          20
504 (1 row)
505
506 SELECT * FROM test_type_conversion_nnint(null, 20);
507 ERROR:  value for domain nnint violates check constraint "nnint_check"
508 SELECT * FROM test_type_conversion_nnint(10, null);
509 ERROR:  value for domain nnint violates check constraint "nnint_check"
510 CONTEXT:  while creating return value
511 PL/Python function "test_type_conversion_nnint"
512 CREATE DOMAIN bytea10 AS bytea CHECK (octet_length(VALUE) = 10 AND VALUE IS NOT NULL);
513 CREATE FUNCTION test_type_conversion_bytea10(x bytea10, y bytea) RETURNS bytea10 AS $$
514 plpy.info(x, type(x))
515 return y
516 $$ LANGUAGE plpython3u;
517 SELECT * FROM test_type_conversion_bytea10('hello wold', 'hello wold');
518 INFO:  (b'hello wold', <class 'bytes'>)
519 CONTEXT:  PL/Python function "test_type_conversion_bytea10"
520  test_type_conversion_bytea10 
521 ------------------------------
522  \x68656c6c6f20776f6c64
523 (1 row)
524
525 SELECT * FROM test_type_conversion_bytea10('hello world', 'hello wold');
526 ERROR:  value for domain bytea10 violates check constraint "bytea10_check"
527 SELECT * FROM test_type_conversion_bytea10('hello word', 'hello world');
528 INFO:  (b'hello word', <class 'bytes'>)
529 CONTEXT:  PL/Python function "test_type_conversion_bytea10"
530 ERROR:  value for domain bytea10 violates check constraint "bytea10_check"
531 CONTEXT:  while creating return value
532 PL/Python function "test_type_conversion_bytea10"
533 SELECT * FROM test_type_conversion_bytea10(null, 'hello word');
534 ERROR:  value for domain bytea10 violates check constraint "bytea10_check"
535 SELECT * FROM test_type_conversion_bytea10('hello word', null);
536 INFO:  (b'hello word', <class 'bytes'>)
537 CONTEXT:  PL/Python function "test_type_conversion_bytea10"
538 ERROR:  value for domain bytea10 violates check constraint "bytea10_check"
539 CONTEXT:  while creating return value
540 PL/Python function "test_type_conversion_bytea10"
541 --
542 -- Arrays
543 --
544 CREATE FUNCTION test_type_conversion_array_int4(x int4[]) RETURNS int4[] AS $$
545 plpy.info(x, type(x))
546 return x
547 $$ LANGUAGE plpython3u;
548 SELECT * FROM test_type_conversion_array_int4(ARRAY[0, 100]);
549 INFO:  ([0, 100], <class 'list'>)
550 CONTEXT:  PL/Python function "test_type_conversion_array_int4"
551  test_type_conversion_array_int4 
552 ---------------------------------
553  {0,100}
554 (1 row)
555
556 SELECT * FROM test_type_conversion_array_int4(ARRAY[0,-100,55]);
557 INFO:  ([0, -100, 55], <class 'list'>)
558 CONTEXT:  PL/Python function "test_type_conversion_array_int4"
559  test_type_conversion_array_int4 
560 ---------------------------------
561  {0,-100,55}
562 (1 row)
563
564 SELECT * FROM test_type_conversion_array_int4(ARRAY[NULL,1]);
565 INFO:  ([None, 1], <class 'list'>)
566 CONTEXT:  PL/Python function "test_type_conversion_array_int4"
567  test_type_conversion_array_int4 
568 ---------------------------------
569  {NULL,1}
570 (1 row)
571
572 SELECT * FROM test_type_conversion_array_int4(ARRAY[]::integer[]);
573 INFO:  ([], <class 'list'>)
574 CONTEXT:  PL/Python function "test_type_conversion_array_int4"
575  test_type_conversion_array_int4 
576 ---------------------------------
577  {}
578 (1 row)
579
580 SELECT * FROM test_type_conversion_array_int4(NULL);
581 INFO:  (None, <class 'NoneType'>)
582 CONTEXT:  PL/Python function "test_type_conversion_array_int4"
583  test_type_conversion_array_int4 
584 ---------------------------------
585  
586 (1 row)
587
588 SELECT * FROM test_type_conversion_array_int4(ARRAY[[1,2,3],[4,5,6]]);
589 ERROR:  cannot convert multidimensional array to Python list
590 DETAIL:  PL/Python only supports one-dimensional arrays.
591 CONTEXT:  PL/Python function "test_type_conversion_array_int4"
592 CREATE FUNCTION test_type_conversion_array_text(x text[]) RETURNS text[] AS $$
593 plpy.info(x, type(x))
594 return x
595 $$ LANGUAGE plpython3u;
596 SELECT * FROM test_type_conversion_array_text(ARRAY['foo', 'bar']);
597 INFO:  (['foo', 'bar'], <class 'list'>)
598 CONTEXT:  PL/Python function "test_type_conversion_array_text"
599  test_type_conversion_array_text 
600 ---------------------------------
601  {foo,bar}
602 (1 row)
603
604 CREATE FUNCTION test_type_conversion_array_bytea(x bytea[]) RETURNS bytea[] AS $$
605 plpy.info(x, type(x))
606 return x
607 $$ LANGUAGE plpython3u;
608 SELECT * FROM test_type_conversion_array_bytea(ARRAY[E'\\xdeadbeef'::bytea, NULL]);
609 INFO:  ([b'\xde\xad\xbe\xef', None], <class 'list'>)
610 CONTEXT:  PL/Python function "test_type_conversion_array_bytea"
611  test_type_conversion_array_bytea 
612 ----------------------------------
613  {"\\xdeadbeef",NULL}
614 (1 row)
615
616 CREATE FUNCTION test_type_conversion_array_mixed1() RETURNS text[] AS $$
617 return [123, 'abc']
618 $$ LANGUAGE plpython3u;
619 SELECT * FROM test_type_conversion_array_mixed1();
620  test_type_conversion_array_mixed1 
621 -----------------------------------
622  {123,abc}
623 (1 row)
624
625 CREATE FUNCTION test_type_conversion_array_mixed2() RETURNS int[] AS $$
626 return [123, 'abc']
627 $$ LANGUAGE plpython3u;
628 SELECT * FROM test_type_conversion_array_mixed2();
629 ERROR:  invalid input syntax for integer: "abc"
630 CONTEXT:  while creating return value
631 PL/Python function "test_type_conversion_array_mixed2"
632 CREATE FUNCTION test_type_conversion_array_record() RETURNS type_record[] AS $$
633 return [None]
634 $$ LANGUAGE plpython3u;
635 ERROR:  PL/Python functions cannot return type type_record[]
636 DETAIL:  PL/Python does not support conversion to arrays of row types.
637 SELECT * FROM test_type_conversion_array_record();
638 ERROR:  function test_type_conversion_array_record() does not exist
639 LINE 1: SELECT * FROM test_type_conversion_array_record();
640                       ^
641 HINT:  No function matches the given name and argument types. You might need to add explicit type casts.
642 CREATE FUNCTION test_type_conversion_array_string() RETURNS text[] AS $$
643 return 'abc'
644 $$ LANGUAGE plpython3u;
645 SELECT * FROM test_type_conversion_array_string();
646  test_type_conversion_array_string 
647 -----------------------------------
648  {a,b,c}
649 (1 row)
650
651 CREATE FUNCTION test_type_conversion_array_tuple() RETURNS text[] AS $$
652 return ('abc', 'def')
653 $$ LANGUAGE plpython3u;
654 SELECT * FROM test_type_conversion_array_tuple();
655  test_type_conversion_array_tuple 
656 ----------------------------------
657  {abc,def}
658 (1 row)
659
660 CREATE FUNCTION test_type_conversion_array_error() RETURNS int[] AS $$
661 return 5
662 $$ LANGUAGE plpython3u;
663 SELECT * FROM test_type_conversion_array_error();
664 ERROR:  return value of function with array return type is not a Python sequence
665 CONTEXT:  while creating return value
666 PL/Python function "test_type_conversion_array_error"
667 ---
668 --- Composite types
669 ---
670 CREATE TABLE employee (
671     name text,
672     basesalary integer,
673     bonus integer
674 );
675 INSERT INTO employee VALUES ('John', 100, 10), ('Mary', 200, 10);
676 CREATE OR REPLACE FUNCTION test_composite_table_input(e employee) RETURNS integer AS $$
677 return e['basesalary'] + e['bonus']
678 $$ LANGUAGE plpython3u;
679 SELECT name, test_composite_table_input(employee.*) FROM employee;
680  name | test_composite_table_input 
681 ------+----------------------------
682  John |                        110
683  Mary |                        210
684 (2 rows)
685
686 ALTER TABLE employee DROP bonus;
687 SELECT name, test_composite_table_input(employee.*) FROM employee;
688 ERROR:  KeyError: 'bonus'
689 CONTEXT:  Traceback (most recent call last):
690   PL/Python function "test_composite_table_input", line 2, in <module>
691     return e['basesalary'] + e['bonus']
692 PL/Python function "test_composite_table_input"
693 ALTER TABLE employee ADD bonus integer;
694 UPDATE employee SET bonus = 10;
695 SELECT name, test_composite_table_input(employee.*) FROM employee;
696  name | test_composite_table_input 
697 ------+----------------------------
698  John |                        110
699  Mary |                        210
700 (2 rows)
701
702 CREATE TYPE named_pair AS (
703     i integer,
704     j integer
705 );
706 CREATE OR REPLACE FUNCTION test_composite_type_input(p named_pair) RETURNS integer AS $$
707 return sum(p.values())
708 $$ LANGUAGE plpython3u;
709 SELECT test_composite_type_input(row(1, 2));
710  test_composite_type_input 
711 ---------------------------
712                          3
713 (1 row)
714
715 ALTER TYPE named_pair RENAME TO named_pair_2;
716 SELECT test_composite_type_input(row(1, 2));
717  test_composite_type_input 
718 ---------------------------
719                          3
720 (1 row)
721
722 --
723 -- Prepared statements
724 --
725 CREATE OR REPLACE FUNCTION test_prep_bool_input() RETURNS int
726 LANGUAGE plpython3u
727 AS $$
728 plan = plpy.prepare("SELECT CASE WHEN $1 THEN 1 ELSE 0 END AS val", ['boolean'])
729 rv = plpy.execute(plan, ['fa'], 5) # 'fa' is true in Python
730 return rv[0]['val']
731 $$;
732 SELECT test_prep_bool_input(); -- 1
733  test_prep_bool_input 
734 ----------------------
735                     1
736 (1 row)
737
738 CREATE OR REPLACE FUNCTION test_prep_bool_output() RETURNS bool
739 LANGUAGE plpython3u
740 AS $$
741 plan = plpy.prepare("SELECT $1 = 1 AS val", ['int'])
742 rv = plpy.execute(plan, [0], 5)
743 plpy.info(rv[0])
744 return rv[0]['val']
745 $$;
746 SELECT test_prep_bool_output(); -- false
747 INFO:  {'val': False}
748 CONTEXT:  PL/Python function "test_prep_bool_output"
749  test_prep_bool_output 
750 -----------------------
751  f
752 (1 row)
753
754 CREATE OR REPLACE FUNCTION test_prep_bytea_input(bb bytea) RETURNS int
755 LANGUAGE plpython3u
756 AS $$
757 plan = plpy.prepare("SELECT octet_length($1) AS val", ['bytea'])
758 rv = plpy.execute(plan, [bb], 5)
759 return rv[0]['val']
760 $$;
761 SELECT test_prep_bytea_input(E'a\\000b'); -- 3 (embedded null formerly truncated value)
762  test_prep_bytea_input 
763 -----------------------
764                      3
765 (1 row)
766
767 CREATE OR REPLACE FUNCTION test_prep_bytea_output() RETURNS bytea
768 LANGUAGE plpython3u
769 AS $$
770 plan = plpy.prepare("SELECT decode('aa00bb', 'hex') AS val")
771 rv = plpy.execute(plan, [], 5)
772 plpy.info(rv[0])
773 return rv[0]['val']
774 $$;
775 SELECT test_prep_bytea_output();
776 INFO:  {'val': b'\xaa\x00\xbb'}
777 CONTEXT:  PL/Python function "test_prep_bytea_output"
778  test_prep_bytea_output 
779 ------------------------
780  \xaa00bb
781 (1 row)
782