DML コマンドの影響を受ける行数の決定

DML コマンド が実行された後( TRUNCATE TABLE コマンドを除く)、Snowflake Scripting は以下のグローバル変数をセットします。これらの変数を使用して、最後の DML ステートメントが行に影響を与えたかどうかを判別できます。

変数

説明

SQLROWCOUNT

最後の DML ステートメントの影響を受けた行の数。

これは、 JavaScript ストアドプロシージャの getNumRowsAffected() と同等です。

SQLFOUND

最後の DML ステートメントが1つ以上の行に影響を与えた場合は true

SQLNOTFOUND

最後の DML ステートメントがゼロ行に影響を与えた場合は true

このセクションの例では、次のテーブルを使用します。

CREATE OR REPLACE TABLE my_values (value NUMBER);
Copy

次の例では、 SQLROWCOUNT 変数を使用して、最後の DML ステートメント(INSERT ステートメント)の影響を受けた行数を返します。SELECT ステートメントは DML ステートメントではなく、 SQLROWCOUNT 変数には影響しません。

BEGIN
  INSERT INTO my_values VALUES (1), (2), (3);
  SELECT * from my_values;
  RETURN SQLROWCOUNT;
END;
Copy

注: SnowSQLClassic Consoleexecute_stream または execute_string メソッドを Python Connector コードで使用している場合は、代わりにこの例を使用してください(SnowSQL、 Classic Console、Python ConnectorでSnowflakeスクリプトを使用する を参照)。

EXECUTE IMMEDIATE $$
BEGIN
  INSERT INTO my_values VALUES (1), (2), (3);
  SELECT * from my_values;
  RETURN SQLROWCOUNT;
END;
$$;
Copy
+-----------------+
| anonymous block |
|-----------------|
|               3 |
+-----------------+

次の例では、 SQLFOUND 変数と SQLNOTFOUND 変数を使用して、最後の DML ステートメント(UPDATE ステートメント)の影響を受ける行数を返します。前の例と同じように、 SELECT ステートメントは SQLFOUNDSQLNOTFOUND 変数に影響を与えません。

BEGIN
  IF ((SELECT MAX(value) FROM my_values) > 2) THEN
    UPDATE my_values SET value = 4 WHERE value < 3;
  END IF;
  SELECT * from my_values;
  IF (SQLFOUND = true) THEN
    RETURN 'Updated ' || SQLROWCOUNT || ' rows.';
  ELSEIF (SQLNOTFOUND = true) THEN
    RETURN 'No rows updated.';
  ELSE
    RETURN 'No DML statements executed.';
  END IF;
END;
Copy

注: SnowSQLClassic Consoleexecute_stream または execute_string メソッドを Python Connector コードで使用している場合は、代わりにこの例を使用してください(SnowSQL、 Classic Console、Python ConnectorでSnowflakeスクリプトを使用する を参照)。

EXECUTE IMMEDIATE $$
BEGIN
  IF ((SELECT MAX(value) FROM my_values) > 2) THEN
    UPDATE my_values SET value = 4 WHERE value < 3;
  END IF;
  SELECT * from my_values;
  IF (SQLFOUND = true) THEN
    RETURN 'Updated ' || SQLROWCOUNT || ' rows.';
  ELSEIF (SQLNOTFOUND = true) THEN
    RETURN 'No rows updated.';
  ELSE
    RETURN 'No DML statements executed.';
  END IF;
END;
$$;
Copy

匿名ブロックが実行されると、 UPDATE ステートメントが2行を更新するため、 SQLFOUND 変数は true になります。

+-----------------+
| anonymous block |
|-----------------|
| Updated 2 rows. |
+-----------------+

現在の値を確認するためにテーブルをクエリします。

SELECT * FROM my_values;
Copy
+-------+
| VALUE |
|-------|
|     4 |
|     4 |
|     3 |
+-------+

同じ匿名ブロックをもう一度実行すると、結果は次のようになります。

  • 2 よりも大きい値がテーブル内にあるため、 UPDATE ステートメントが実行されます。つまり、 IF の条件は満たされています。

  • 行が更新されていないため、変数 SQLNOTFOUNDtrue です。テーブル内のどの値も 3 (WHERE 句で指定)より小さいため、 UPDATE ステートメントは行を更新しません。

クエリは次の出力を返します。

+------------------+
| anonymous block  |
|------------------|
| No rows updated. |
+------------------+

次に、テーブルを更新し、すべての値を 1 にセットします:

UPDATE my_values SET value = 1;

SELECT * FROM my_values;
Copy
+-------+
| VALUE |
|-------|
|     1 |
|     1 |
|     1 |
+-------+

同じ匿名ブロックを再度実行すると、 UPDATE ステートメントは実行されません。なぜなら、テーブル内のどの値も 2 よりも大きくないからです。つまり、 IF の条件が満たされていないので、 UPDATE ステートメントは実行されません。

+-----------------------------+
| anonymous block             |
|-----------------------------|
| No DML statements executed. |
+-----------------------------+