Условное нарушение Snowflake Snowsql, ЕСЛИ, ПЕРЕКЛЮЧИТЬ

#snowflake-cloud-data-platform #snowsql

#снежинка-облачная платформа для обработки данных #snowsql #snowflake-облачная платформа для обработки данных

Вопрос:

Вопрос касается Snowflake snowsql. И нужно выполнить условную проверку, чтобы увидеть, вставлен ли ETL_Date уже в таблицу, и если он есть; выйдите из сохраненной процедуры. В противном случае, если дата не вставлена, продолжайте и вставьте данные, а затем верните успех (ноль) и завершите работу. Любая помощь будет очень признательна. Спасибо.

Отправная точка: то, что я сделал до сих пор в своем коде.

 IF ((SELECT IFNULL(MAX(ETL_DATE),'1900-01-01') FROM DB.TABLES.test_20200909) > CURRENT_DATE() )
{RETURN 0; break;}
else insert into DB.TABLES.test_20200909 (ETL_DATE,INSERT_VALUE)
values(CURRENT_DATE(),1)
  

И это выдает мне ошибку: ошибка компиляции SQL: синтаксическая ошибка строки 1 в позиции 0 неожиданное ‘IF’.

Цель / Конец игры: Нужно поместить это в сохраненный процесс. То, что я изложил до сих пор, это:

 CREATE or replace procedure   TABLE_DB.TABLES.test_20200909_1 ()
returns FLOAT
language javascript
as
$$

var test_1 =`IF ((SELECT MAX(ETL_DATE) FROM DB.TABLES.test_20200909) > CURRENT_DATE() )
{RETURN 0; break;}
else insert into DB.TABLES.test_20200909 (ETL_DATE,INSERT_VALUE)
values(CURRENT_DATE(),1)`;
var test_1_stmt =  snowflake.createStatement({sqlText: test_1});  
var test_1_res = test_1_stmt.execute();
return 0
$$
  

Ответ №1:

Если ваша цель — создать хранимую процедуру для проверки / управления вашей загрузкой, я бы создал ее следующим образом :

 create or replace procedure SP_CHECK_LOAD()
    RETURNS VARCHAR(256) NOT NULL
    LANGUAGE JAVASCRIPT
    EXECUTE AS CALLER
as $$    

function get_check_load()
{
    var v_out_check_load;
    rs = snowflake.execute ( { sqlText: `SELECT CASE WHEN MAX(ETL_DATE)>=CURRENT_DATE() THEN 0 ELSE 1 END AS CHECK_RESULT FROM DB.TABLES.test_20200909;` }  );
    if( rs.next())
    {
       v_out_check_load = rs.getColumnValue(1); // get check result
    }

    return v_out_check_load; 
}   
  
  var result = new String('Successfully Executed');
  var v_check = get_check_load();
  
  if ( v_check==1 )
  {
    //data not yet loaded -> load them
    try {
       
    var sql_command = `INSERT INTO DB.TABLES.test_20200909 (ETL_DATE,INSERT_VALUE) VALUES(CURRENT_DATE(),1)`;
 
    var stmt = snowflake.createStatement({sqlText: sql_command});
    var res = stmt.execute();  
    
    }
    catch (err) {
    result =  "Failed: Code: "   err.code   " | State: "   err.state;
    result  = "n  Message: "   err.message;
    result  = "nStack Trace:n"   err.stackTraceTxt; 
    } 
 } // end if
 
 return result;

  $$;
  

Пожалуйста, обратите внимание, что я использовал >= внутри условия проверки MAX(ETL_DATE)>=CURRENT_DATE(), а не только > как в вашем примере, потому что в этом случае вы исключили бы загрузку текущей даты. Измените его, если это не соответствует вашим потребностям.

Комментарии:

1. Спасибо @Saul, я попробую это.

Ответ №2:

Исходя из того, что вы упомянули, похоже, что вам даже не нужна хранимая процедура для этого. Вы можете использовать сопоставление слиянием, которое, вероятно, проще настроить

И нужно выполнить условную проверку, чтобы увидеть, вставлен ли ETL_Date уже в таблицу, и если он есть; выйдите из сохраненной процедуры. ИНАЧЕ, если дата не вставлена, продолжайте вставлять данные, а затем возвращайте успех (ноль)

Пожалуйста, посмотрите, есть ли ниже то, чего вы пытаетесь достичь

 CREATE OR REPLACE TABLE test_20200909(INSERT_VALUE NUMBER, ETL_DATE TIMESTAMP);
 
INSERT INTO TEST_20200909 VALUES(1, '2020-09-01 00:00:00.000');
INSERT INTO TEST_20200909 VALUES(1, '2020-09-02 00:00:00.000');
INSERT INTO TEST_20200909 VALUES(1, '2020-09-03 00:00:00.000');
INSERT INTO TEST_20200909 VALUES(1, '2020-09-04 00:00:00.000');
 
SELECT * FROM test_20200909;
 
MERGE INTO test_20200909 T
 USING(SELECT MAX(ETL_DATE) maxdate FROM test_20200909) S 
 ON S.maxdate=CURRENT_DATE()
 when NOT matched then 
  insert (INSERT_VALUE,ETL_DATE)  values (1, CURRENT_DATE());
  
SELECT * FROM test_20200909;
  

Комментарии:

1. Спасибо @Rajib ; Я тоже попробую это. К сожалению, мне действительно нужен сохраненный процесс. Поскольку решение, которое я представил выше, является самым простым; после этого предложения IF есть другие логические инструкции select, которые выполняют фактическую вставку в таблицу.

2. Конечно, вы можете встроить этот запрос на слияние также в свою процедуру, это поможет вам сократить код. Дайте нам знать, как вы, наконец, решите эту проблему.

3. Привет, СЛИЯНИЕ Rajib работает так же хорошо; и был ли это MS-SQL; был бы единственным способом, которым я бы объединил данные. К сожалению (и я действительно это имею в виду), я переношу код на Snowflake. И бизнесу нужен хранимый процесс.