DECLARE
Define um novo cursor. Use um cursor para recuperar algumas linhas de cada vez do conjunto de resultados de uma consulta maior.
Quando a primeira linha do cursor é buscada, o conjunto inteiro de resultados é materializado no nó líder, na memória ou em disco, se necessário. Devido ao impacto da performance negativa potencial de usar cursores com grandes conjuntos de resultado, recomendamos abordagens alternativas sempre que possível. Para obter mais informações, consulte Considerações sobre a performance ao usar cursores.
Você deve declarar um cursor em um bloco de transação. Apenas um cursor pode ser aberto por sessão.
Para obter mais informações, consulte FETCHCLOSE.
Sintaxe
DECLARE cursor_name CURSOR FOR query
Parâmetros
- nome_cursor
-
Nome do novo cursor.
- query
-
Uma instrução SELECT que preenche o cursor.
Observações de uso de DECLARE CURSOR
Se seu aplicativo cliente usa uma conexão ODBC e sua consulta cria um conjunto de resultados que é muito grande para caber na memória, você pode transmitir o conjunto de resultados para seu aplicativo cliente usando um cursor. Quando você usa um cursor, o conjunto inteiro de resultados é materializado no nó líder, e a partir de então seu cliente pode buscar os resultados adicionais.
nota
Para permitir cursores em ODBC para Microsoft Windows, habilite a opção Use Declare/Fetch no DSN ODBC que você usa para o Amazon Redshift. Recomendamos configurar o tamanho do cache de ODBC usando o campo Cache Size nas opções da caixa de diálogo do DSN de ODBC, para 4.000 ou superior em clusters de nós múltiplos para minimizar round trips. Em um cluster de nó único, defina o tamanho do cache para 1.000.
Devido ao impacto da performance negativa potencial do uso de cursores, recomendamos abordagens alternativas sempre que possível. Para obter mais informações, consulte Considerações sobre a performance ao usar cursores.
Os cursores do Amazon Redshift são compatíveis com as seguintes restrições:
-
Apenas um cursor pode ser aberto por sessão.
-
Os cursores devem ser usados em uma transação (BEGIN … END).
-
O tamanho máximo do conjunto de resultados cumulativo para todos os cursores é restringido com base no tipo de nó do cluster. Se você precisar de conjuntos de resultados maiores, é possível redimensionar o tamanho para uma configuração de nó XL ou 8XL.
Para obter mais informações, consulte Restrições de cursor.
Restrições de cursor
Quando a primeira linha de um cursor é buscada, o conjunto inteiro de resultados é materializado no nó líder. Se o resultado não couber na memória, ele será gravado em disco conforme necessário. Para proteger a integridade do nó líder, o Amazon Redshift aplica restrições de tamanho a todos os conjuntos de resultados de cursor com base no tipo de nó do cluster.
A tabela a seguir mostra o tamanho total máximo do conjunto de resultados para cada tipo de nó do cluster. O tamanho máximo do conjunto de resultados é fornecido em megabytes.
Tipo de nó | Conjunto máximo de resultados por cluster (MB) |
---|---|
Vários nós DC2 Large |
192.000 |
Nó simples DC2 Large |
8.000 |
Vários nós 8XL DC2 |
3.200.000 |
Vários nós RA3 16XL |
14.400.000 |
Vários nós RA3 4XL |
3.200.000 |
Vários nós do RA3 XLPLUS |
1.000.000 |
Nó único RA3 XLPLUS |
64.000 |
Vários nós RA3 LARGE |
240.000 |
Nó único RA3 LARGE |
8.000 |
Amazon Redshift sem servidor |
150.000 |
Para visualizar a configuração de cursor ativa para um cluster, consulte a tabela de sistema STV_CURSOR_CONFIGURATION como superusuário. Para exibir o estado de cursores ativos, consulte a tabela de sistema STV_ACTIVE_CURSORS. Somente as linhas dos cursores do próprio usuário são visíveis para ele, mas um superusuário pode visualizar todos os cursores.
Considerações sobre a performance ao usar cursores
Como os cursores materializam o conjunto de resultados inteiro no nó líder antes de começar a retornar resultados para o cliente, usar cursores com conjuntos muito grandes de resultados pode ter um impacto negativo na performance. É altamente recomendável não usar cursores com conjuntos muito grandes de resultados. Em alguns casos, como quando seu aplicativo usa uma conexão ODBC, os cursores podem ser a única solução viável. Se possível, recomendamos o uso destas alternativas:
-
Use UNLOAD para exportar uma tabela grande. Quando você usa UNLOAD, os nós de computação funcionam em paralelo para transferir os dados diretamente para arquivos de dados no Amazon Simple Storage Service. Para obter mais informações, consulte Descarregar dados no Amazon Redshift.
-
Defina o parâmetro de tamanho de busca JDBC no seu aplicativo cliente. Se você utiliza uma conexão JDBC e estiver encontrando erros de falta de memória por parte do cliente, é possível habilitar seu cliente para recuperar conjuntos de resultados em lotes menores configurando o parâmetro de tamanho de busca JDBC. Para ter mais informações, consulte Como configurar o parâmetro JDBC para o tamanho da busca.
Exemplo de DECLARE CURSOR
O exemplo a seguir declara um cursor denominado LOLLAPALOOZA para selecionar informações de vendas para o evento Lollapalooza e busca linhas do conjunto de resultados usando o cursor:
-- Begin a transaction begin; -- Declare a cursor declare lollapalooza cursor for select eventname, starttime, pricepaid/qtysold as costperticket, qtysold from sales, event where sales.eventid = event.eventid and eventname='Lollapalooza'; -- Fetch the first 5 rows in the cursor lollapalooza: fetch forward 5 from lollapalooza; eventname | starttime | costperticket | qtysold --------------+---------------------+---------------+--------- Lollapalooza | 2008-05-01 19:00:00 | 92.00000000 | 3 Lollapalooza | 2008-11-15 15:00:00 | 222.00000000 | 2 Lollapalooza | 2008-04-17 15:00:00 | 239.00000000 | 3 Lollapalooza | 2008-04-17 15:00:00 | 239.00000000 | 4 Lollapalooza | 2008-04-17 15:00:00 | 239.00000000 | 1 (5 rows) -- Fetch the next row: fetch next from lollapalooza; eventname | starttime | costperticket | qtysold --------------+---------------------+---------------+--------- Lollapalooza | 2008-10-06 14:00:00 | 114.00000000 | 2 -- Close the cursor and end the transaction: close lollapalooza; commit;
O exemplo a seguir percorre um refcursor com todos os resultados de uma tabela:
CREATE TABLE tbl_1 (a int, b int); INSERT INTO tbl_1 values (1, 2),(3, 4); CREATE OR REPLACE PROCEDURE sp_cursor_loop() AS $$ DECLARE target record; curs1 cursor for select * from tbl_1; BEGIN OPEN curs1; LOOP fetch curs1 into target; exit when not found; RAISE INFO 'a %', target.a; END LOOP; CLOSE curs1; END; $$ LANGUAGE plpgsql; CALL sp_cursor_loop(); SELECT message from svl_stored_proc_messages where querytxt like 'CALL sp_cursor_loop()%'; message ---------- a 1 a 3