我想在函数中检索自定义类型,并将其用作另一个函数的参数来复制记录。在下面的代码中,我展示了检索自定义类型并将其用作函数的参数都成功:分别参见getWholeWeatherData()和addWholeWeatherData()。
有关问题,请参阅dupwd()。如何将getWholeWeatherData()中自定义类型的输出作为参数传递给addWholeWeatherData(),两者都可以自行成功。
$ psql --version psql(PostgreSQL)9.3.0
DROP TABLE IF EXISTS wd;
DROP TYPE IF EXISTS wtype CASCADE;
CREATE TYPE wtype AS (
latitude NUMERIC,
longitude NUMERIC,
temp NUMERIC,
barometer NUMERIC
);
DROP FUNCTION IF EXISTS getWholeWeatherData(INTEGER);
DROP FUNCTION IF EXISTS addWholeWeatherData(wtype);
DROP FUNCTION IF EXISTS dupwd(INTEGER);
DROP FUNCTION IF EXISTS tryAddWholeWeatherData();
CREATE TABLE wd
(
wo_id SERIAL PRIMARY KEY,
datetime TIMESTAMP NOT NULL,
latitude NUMERIC(9, 6) NOT NULL,
longitude NUMERIC(9, 6) NOT NULL,
temp NUMERIC(4, 1),
barometer NUMERIC(4, 2),
comment TEXT
);
CREATE OR REPLACE FUNCTION getWholeWeatherData(observ_id INTEGER)
RETURNS wtype AS $$
DECLARE
returnrec wtype%ROWTYPE;
BEGIN
SELECT INTO returnrec
latitude,
longitude,
temp,
barometer
FROM wd WHERE wo_id = observ_id;
RETURN returnrec;
END;
$$ LANGUAGE plpgsql;
-- This works
CREATE OR REPLACE FUNCTION addWholeWeatherData(weather wtype)
RETURNS INTEGER AS $$
DECLARE
observ_id INTEGER;
BEGIN
INSERT INTO wd (
datetime,
latitude,
longitude,
temp,
barometer,
comment
)
VALUES (
localtimestamp,
weather.latitude,
weather.longitude,
weather.temp,
weather.barometer,
'just a test'
)
RETURNING wo_id INTO observ_id;
RETURN observ_id;
END;
$$ LANGUAGE plpgsql;
-- This works
CREATE OR REPLACE FUNCTION tryAddWholeWeatherData()
RETURNS INTEGER AS $$
DECLARE
wdd wtype;
woid INTEGER;
BEGIN
wdd.longitude = 99.99999;
wdd.latitude = 88.88888;
wdd.temp = 77.77;
wdd.barometer = 66.666;
SELECT INTO woid addWholeWeatherData(wdd);
RETURN woid;
END;
$$ LANGUAGE plpgsql;
-- This is the question
CREATE OR REPLACE FUNCTION dupwd(observ_id INTEGER)
RETURNS VOID AS $$
DECLARE
dr wtype;
BEGIN
-- ??? How to get wtype result from getWholeWeatherData() into variable dr wtype
SELECT INTO dr getWholeWeatherData(observ_id);
-- ??? This should work if I could get the value for dr from getWholeWeatherData()
SELECT addWholeWeatherData(dr);
END;
$$ LANGUAGE plpgsql;
-- Get started with a record
INSERT INTO wd (
datetime,
latitude,
longitude,
temp,
barometer,
comment
)
VALUES (
localtimestamp,
12.3456,
23.4567,
123,
29.345,
'initial data'
);
SELECT * FROM wd;
-- Successfully retrieves a wtype record
SELECT getWholeWeatherData(1);
-- Successfully adds a wtype record
--SELECT tryAddWholeWeatherData();
-- duplicate a record
SELECT dupwd(1);
SELECT * FROM wd;
以下是运行脚本的输出:
INSERT 0 1
wo_id | datetime | latitude | longitude | temp | barometer | comment
-------+----------------------------+-----------+-----------+-------+-----------+--------------
1 | 2013-12-07 13:18:14.127465 | 12.345600 | 23.456700 | 123.0 | 29.35 | initial data
(1 row)
getwholeweatherdata
-----------------------------------
(12.345600,23.456700,123.0,29.35)
(1 row)
tryaddwholeweatherdata
------------------------
2
(1 row)
wo_id | datetime | latitude | longitude | temp | barometer | comment
-------+----------------------------+-----------+-----------+-------+-----------+--------------
1 | 2013-12-07 13:18:14.127465 | 12.345600 | 23.456700 | 123.0 | 29.35 | initial data
2 | 2013-12-07 13:18:14.129907 | 88.888880 | 99.999990 | 77.8 | 66.67 | just a test
(2 rows)
psql:q1.sql:126: ERROR: invalid input syntax for type numeric: "(12.345600,23.456700,123.0,29.35)"
CONTEXT: PL/pgSQL function dupwd(integer) line 6 at SQL statement
wo_id | datetime | latitude | longitude | temp | barometer | comment
-------+----------------------------+-----------+-----------+-------+-----------+--------------
1 | 2013-12-07 13:18:14.127465 | 12.345600 | 23.456700 | 123.0 | 29.35 | initial data
2 | 2013-12-07 13:18:14.129907 | 88.888880 | 99.999990 | 77.8 | 66.67 | just a test
(2 rows)
答案 0 :(得分:1)
在plpgsql函数中,当调用函数并想要丢弃返回值时,必须使用PERFORM
代替SELECT
。
所以,在你的函数dupwd()
中:
SELECT addWholeWeatherData(dr);
PERFORM addWholeWeatherData(dr);
当然,您可以简化通话。对于所呈现的简单情况,您不需要中间变量。你甚至不需要一个单独的功能。只是:
SELECT addWholeWeatherData(getWholeWeatherData(observ_id));