Updated on 2024-05-07 GMT+08:00

FETCH

Description

FETCH retrieves rows using a previously created cursor.

A cursor has an associated position, which is used by FETCH. The cursor position can be before the first row of the query result, on any particular row of the result, or after the last row of the result.

  • When created, a cursor is positioned before the first row.
  • After fetching some rows, the cursor is positioned on the row most recently retrieved.
  • If FETCH runs off the end of the available rows then the cursor is left positioned after the last row, or before the first row if fetching backward.
  • FETCH ALL or FETCH BACKWARD ALL will always leave the cursor positioned after the last row or before the first row.

Precautions

  • If the cursor is declared with NO SCROLL, backward fetches like FETCH BACKWARD are not allowed.
  • The forms NEXT, PRIOR, FIRST, LAST, ABSOLUTE, and RELATIVE fetch a single row after moving the cursor appropriately. If there is no such row, an empty result is returned, and the cursor is left positioned before the first row (backward fetch) or after the last row (forward fetch) as appropriate.
  • The forms using FORWARD and BACKWARD retrieve the indicated number of rows moving in the forward or backward direction, leaving the cursor positioned on the last-returned row or after (backward fetch)/before (forward fetch) all rows if the count exceeds the number of rows available.
  • RELATIVE 0, FORWARD 0, and BACKWARD 0 all request fetching the current row without moving the cursor, that is, re-fetching the most recently fetched row. This will succeed unless the cursor is positioned before the first row or after the last row; in which case, no row is returned.
  • If the cursor of FETCH involves a non-system catalog, backward fetches like BACKWARD, PRIOR, and FIRST are not allowed.

Syntax

FETCH [ direction { FROM | IN } ] cursor_name;

The direction clause specifies optional parameters.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
NEXT
   | PRIOR
   | FIRST
   | LAST
   | ABSOLUTE count
   | RELATIVE count
   | count
   | ALL
   | FORWARD
   | FORWARD count
   | FORWARD ALL
   | BACKWARD
   | BACKWARD count
   | BACKWARD ALL

Parameters

  • direction_clause

    Defines the fetch direction.

    Value range:

    • NEXT (default value)

      Fetches the next row.

    • PRIOR

      Fetches the prior row.

    • FIRST

      Fetches the first row of the query (same as ABSOLUTE 1).

    • LAST

      Fetches the last row of the query (same as ABSOLUTE -1).

    • ABSOLUTE count

      Fetches the count'th row of the query.

      ABSOLUTE fetches are not any faster than navigating to the desired row with a relative move: the underlying implementation must traverse all the intermediate rows anyway.

      Value range: a possibly-signed integer

      • If count is positive, the count'th row of the query will be fetched. If count is less than the current cursor position, rewind is required, which is currently not supported.
      • If count is negative or 0, backward scanning is required, which is currently not supported.
    • RELATIVE count

      Fetches the count'th succeeding row or the count'th prior row if count is negative.

      Value range: a possibly-signed integer

      • If count is positive, the count'th succeeding row will be fetched.
      • If count is negative or 0, backward scanning is required, which is currently not supported.
      • If the current row contains no data, RELATIVE 0 returns null.
    • count

      Fetches the next count rows (same as FORWARD count).

    • ALL

      Fetches all remaining rows (same as FORWARD ALL).

    • FORWARD

      Fetches the next row (same as NEXT).

    • FORWARD count

      Fetches the next or prior count rows (same as RELATIVE count).

    • FORWARD ALL

      Fetches all remaining rows.

    • BACKWARD

      Fetches the prior row (same as PRIOR).

    • BACKWARD count

      Fetches the prior count rows (scanning backwards).

      Value range: a possibly-signed integer

      • If count is positive, count prior rows will be fetched.
      • If count is a negative, count succeeding rows will be fetched.
      • BACKWARD 0 re-fetches the current row, if any.
    • BACKWARD ALL

      Fetches all prior rows (scanning backwards).

  • { FROM | IN } cursor_name

    Specifies the cursor name using the keyword FROM or IN.

    Value range: an existing cursor name

Examples

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
-- Create a schema.
gaussdb=# CREATE SCHEMA tpcds;
 
-- Create the tpcds.customer_address table.
gaussdb=# CREATE TABLE tpcds.customer_address
(
ca_address_sk         INTEGER           NOT NULL,
ca_address_id         CHARACTER(16)     NOT NULL,
ca_street_number      INTEGER                    ,
ca_street_name        CHARACTER (20)
);
 
  -- Insert multiple records into the table.
gaussdb=# INSERT INTO tpcds.customer_address VALUES (1, 'AAAAAAAABAAAAAAA', '18', 'Jackson'),(2, 'AAAAAAAACAAAAAAA', '362', 'Washington 6th'),(3, 'AAAAAAAADAAAAAAA', '585', 'Dogwood Washington');

-- (For the SELECT statement, traverse a table using a cursor.) Start a transaction.
gaussdb=# START TRANSACTION;

-- Set up cursor1.
gaussdb=# CURSOR cursor1 FOR SELECT * FROM tpcds.customer_address ORDER BY 1;

-- Fetch the first three rows in cursor1.
gaussdb=# FETCH FORWARD 3 FROM cursor1;
 ca_address_sk |  ca_address_id   | ca_street_number |   ca_street_name      
---------------+------------------+------------------+--------------------
             1 | AAAAAAAABAAAAAAA | 18               | Jackson                           
             2 | AAAAAAAACAAAAAAA | 362              | Washington 6th                    
             3 | AAAAAAAADAAAAAAA | 585              | Dogwood Washington        
(3 rows)

-- Close the cursor and commit the transaction.
gaussdb=# CLOSE cursor1;

-- End the transaction.
gaussdb=# END;

-- (For the VALUES clause, traverse the clause using a cursor.) Start a transaction.
gaussdb=# START TRANSACTION;

-- Set up cursor2.
gaussdb=# CURSOR cursor2 FOR VALUES(1,2),(0,3) ORDER BY 1;

-- Fetch the first two rows in cursor2.
gaussdb=# FETCH FORWARD 2 FROM cursor2;
column1 | column2
---------+---------
0 |       3
1 |       2
(2 rows)

-- Close the cursor and commit the transaction.
gaussdb=# CLOSE cursor2;

-- End the transaction.
gaussdb=# END;

-- (WITH HOLD cursor) Start a transaction.
gaussdb=# START TRANSACTION;

-- Set up a WITH HOLD cursor.
gaussdb=# DECLARE cursor1 CURSOR WITH HOLD FOR SELECT * FROM tpcds.customer_address ORDER BY 1;

-- Fetch the first two rows in cursor1.
gaussdb=# FETCH FORWARD 2 FROM cursor1;
 ca_address_sk |  ca_address_id   | ca_street_number |   ca_street_name      
---------------+------------------+------------------+--------------------
             1 | AAAAAAAABAAAAAAA | 18               | Jackson                           
             2 | AAAAAAAACAAAAAAA | 362              | Washington 6th                    
(2 rows)

-- End the transaction.
gaussdb=# END;

-- Fetch the next row in cursor1.
gaussdb=# FETCH FORWARD 1 FROM cursor1;
 ca_address_sk |  ca_address_id   | ca_street_number |   ca_street_name      
---------------+------------------+------------------+--------------------
             3 | AAAAAAAADAAAAAAA | 585              | Dogwood Washington        
(1 row)

-- Close the cursor.
gaussdb=# CLOSE cursor1;

-- Delete the tpcds.customer_address table.
gaussdb=# DROP TABLE tpcds.customer_address;

-- Delete a schema.
gaussdb=# DROP SCHEMA tpcds CASCADE;

Helpful Links

CLOSE and MOVE