SnowConvert AI – SQL Server – CREATE FUNCTION

Übersetzungsreferenz für die benutzerdefinierten Transact-SQL-Funktionen

Applies to
  • SQL Server

  • Azure Synapse Analytics

Beschreibung

SQL Server unterstützt nur zwei Arten von benutzerdefinierten Funktionen:

Anhand dieser UDFs-Typen ist es möglich, sie nach der inneren Logik in einfach und komplex, zu unterteilen.

Einfache UDFs, gleicht die SQL Server-Syntax mit der Snowflake-Syntax ab. Dieser Typ fügt keine Logik hinzu und führt direkt zum Ergebnis. Diese entsprechen in der Regel den SQL UDFs von Snowflake. SnowConvert unterstützt die Übersetzung von benutzerdefinierten SQL Server-Skalarfunktionen direkt in Snowflake Scripting-UDFs, wenn sie bestimmte Kriterien erfüllen.\ \ Komplexe UDFs, nutzt umfassend eine bestimmte Anweisung (INSERT, DELETE, UPDATE, SET, DECLARE usw.) oder control-of-flow blocks (IF…ELSE, WHILE usw.) und stellt in der Regel eine Nichtübereinstimmung oder einen Verstoß gegenüber der Definition für SQL UDFs von Snowflake dar.

Einschränkungen

Transact UDFs haben einige Beschränkungen, die in anderen Datenbank-Engines (wie Oracle und Teradata) nicht vorhanden sind. Diese Beschränkungen helfen bei der Übersetzung, indem sie das Ausmaß der Fehler eingrenzen. Das bedeutet, dass es bestimmte Szenarien gibt, die wir vermeiden sollten.

Hier sind einige der Beschränkungen, die SQL Server für UDFs hat

  • UDFs können nicht verwendet werden, um Aktionen durchzuführen, die den Zustand der Datenbank verändern

  • Benutzerdefinierte Funktionen können keine OUTPUT INTO-Klausel enthalten, die eine Tabelle als Ziel hat

  • Benutzerdefinierte Funktionen können nicht mehrere Resultsets zurückgeben. Verwenden Sie eine gespeicherte Prozedur, wenn Sie mehrere Resultsets zurückgeben müssen.

Die vollständige Liste finden Sie unter diesem Link Benutzerdefinierte Funktionen erstellen (Datenbank-Engine)

scalar.md

inline-table-valued.md

INLINE TABLE-VALUED

Übersetzungsreferenz zur Konvertierung von Transact-SQL UDF (benutzerdefinierten Funktionen) mit dem TABLE-Rückgabetyp an Snowflake.

Applies to
  • SQL Server

  • Azure Synapse Analytics

Beschreibung

Bemerkung

Einige Teile des Ausgabecodes wurden aus Gründen der Übersichtlichkeit weggelassen.

Inline-Funktionen mit Tabellenwerten sind Tabellenausdrücke, die Parameter akzeptieren, eine SELECT-Anweisung ausführen und ein TABLE zurückgeben können (SQL Server-Referenz: Erstellen einer Inline-Funktion mit Tabellenwerten).

Transact-Syntax

 -- Transact-SQL Inline Table-Valued Function Syntax
CREATE [ OR ALTER ] FUNCTION [ schema_name. ] function_name
( [ { @parameter_name [ AS ] [ type_schema_name. ] parameter_data_type
    [ = default ] [ READONLY ] }
    [ ,...n ]
  ]
)
RETURNS TABLE
    [ WITH <function_option> [ ,...n ] ]
    [ AS ]
    RETURN [ ( ] select_stmt [ ) ]
[ ; ]
Copy

Snowflake SQL-Syntax

CREATE OR REPLACE FUNCTION <name> ( [ <arguments> ] )
  RETURNS TABLE ( <output_col_name> <output_col_type> [, <output_col_name> <output_col_type> ... ] )
  AS '<sql_expression>'sql
Copy

Beispielhafte Quellcode-Muster

Der folgende Abschnitt beschreibt alle möglichen Quelltextmuster, die in dieser Art von CREATE FUNCTION-Syntax vorkommen können.

Für Inline-Funktionen mit Tabellenwerten kann es nur eine Anweisung pro Body geben, die wie folgt aussehen kann:

  • SELECT-Anweisung

  • Allgemeiner TabellenausdruckWITH

Werte direkt aus einer Tabelle auswählen und zurückgeben

Dies ist das einfachste Szenario, bei dem Sie einen einfachen Select aus einer Tabelle durchführen und die Werte zurückgeben

Transact-SQL
Tabellenwertfunktion mit Inline-Anweisungen
CREATE FUNCTION GetDepartmentInfo()
RETURNS TABLE
AS
RETURN
(
  SELECT DepartmentID, Name, GroupName
  FROM HumanResources.Department
);

GO

SELECT * from GetDepartmentInfo()
Copy
Ergebnis

DepartmentID

Name

GroupName

1

Engineering

Research and Development

2

Tool Design

Research and Development

3

Sales

Sales and Marketing

4

Marketing

Sales and Marketing

5

Purchasing

Inventory Management

6

Research and Development

Research and Development

7

Produktion

Manufacturing

8

Production Control

Manufacturing

9

Human Resources

Executive General and Administration

10

Finanzen

Executive General and Administration

11

Information Services

Executive General and Administration

12

Document Control

Quality Assurance

13

Quality Assurance

Quality Assurance

14

Facilities and Maintenance

Executive General and Administration

15

Shipping and Receiving

Inventory Management

16

Executive

Executive General and Administration

Snowflake SQL
Tabellenwertfunktion mit Inline-Anweisungen
CREATE OR REPLACE FUNCTION GetDepartmentInfo ()
RETURNS TABLE(
  DepartmentID STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN DepartmentID WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
  Name STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN Name WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
  GroupName STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN GroupName WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/
)
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},{"attributes":{"component":"transact"}}'
AS
$$
    SELECT
    CAST(DepartmentID AS STRING),
    CAST(Name AS STRING),
    CAST(GroupName AS STRING)
    FROM
    HumanResources.Department
$$;

SELECT
    *
from
    TABLE(GetDepartmentInfo());
Copy
Ergebnis

DepartmentID

Name

GroupName

1

Engineering

Research and Development

2

Tool Design

Research and Development

3

Sales

Sales and Marketing

4

Marketing

Sales and Marketing

5

Purchasing

Inventory Management

6

Research and Development

Research and Development

7

Produktion

Manufacturing

8

Production Control

Manufacturing

9

Human Resources

Executive General and Administration

10

Finanzen

Executive General and Administration

11

Information Services

Executive General and Administration

12

Document Control

Quality Assurance

13

Quality Assurance

Quality Assurance

14

Facilities and Maintenance

Executive General and Administration

15

Shipping and Receiving

Inventory Management

16

Executive

Executive General and Administration

Wählen Sie Werte aus mehreren Tabellen aus und geben Sie sie zurück, indem Sie Spalten umbenennen und eingebaute Funktionen verwenden

Dies ist ein Beispiel für eine Abfrage mit integrierten Funktionen in einer SELECT-Anweisung, die Daten aus verschiedenen Tabellen abruft, Spalten umbenennt und eine Tabelle zurückgibt.

Transact-SQL
Tabellenwertfunktion mit Inline-Anweisungen
CREATE FUNCTION GetPersonBasicInfo()
RETURNS TABLE
AS 
RETURN
( 
 SELECT TOP (20)
      P.PersonType,
      P.FirstName,
      E.JobTitle,
   E.Gender,
      YEAR(E.HireDate) as HIREYEAR
  FROM 
      Person.Person P
  INNER JOIN 
      HumanResources.Employee E
  ON
      P.BusinessEntityID = E.BusinessEntityID 
);

GO

SELECT * FROM GetPersonBasicInfo();
Copy
Ergebnis

PersonType

FirstName

JobTitle

Geschlecht

HIREYEAR

EM

Ken

Chief Executive Officer

M

2009

EM

Terri

Vice President of Engineering

F

2008

EM

Roberto

Engineering Manager

M

2007

EM

Rob

Senior Tool Designer

M

2007

EM

Gail

Design Engineer

F

2008

EM

Jossef

Design Engineer

M

2008

EM

Dylan

Research and Development Manager

M

2009

EM

Diane

Research and Development Engineer

F

2008

EM

Gigi

Research and Development Engineer

F

2009

EM

Michael

Research and Development Manager

M

2009

EM

Ovidiu

Senior Tool Designer

M

2010

EM

Thierry

Tool Designer

M

2007

EM

Janice

Tool Designer

F

2010

EM

Michael

Senior Design Engineer

M

2010

EM

Sharon

Design Engineer

F

2011

EM

David

Marketing Manager

M

2007

EM

Kevin

Marketing Assistant

M

2007

EM

John

Marketing Specialist

M

2011

EM

Maria

Marketing Assistant

F

2011

EM

Wanida

Marketing Assistant

F

2011

Snowflake SQL
Tabellenwertfunktion mit Inline-Anweisungen
CREATE OR REPLACE FUNCTION GetPersonBasicInfo ()
RETURNS TABLE(
 PersonType STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN PersonType WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
 FirstName STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN FirstName WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
 JobTitle STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN JobTitle WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
 Gender STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN Gender WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
 HIREYEAR INTEGER
)
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},{"attributes":{"component":"transact"}}'
AS
$$
  SELECT
  TOP 20
  CAST(P.PersonType AS STRING),
  CAST(P.FirstName AS STRING),
  CAST(E.JobTitle AS STRING),
  CAST(E.Gender AS STRING),
  YEAR(E.HireDate :: TIMESTAMP) as HIREYEAR
   FROM
  Person.Person P
   INNER JOIN
   HumanResources.Employee E
   ON P.BusinessEntityID = E.BusinessEntityID
$$;

SELECT
  *
FROM
  TABLE(GetPersonBasicInfo());
Copy
Ergebnis

PersonType

FirstName

JobTitle

Geschlecht

HIREYEAR

EM

Ken

Chief Executive Officer

M

2009

EM

Terri

Vice President of Engineering

F

2008

EM

Roberto

Engineering Manager

M

2007

EM

Rob

Senior Tool Designer

M

2007

EM

Gail

Design Engineer

F

2008

EM

Jossef

Design Engineer

M

2008

EM

Dylan

Research and Development Manager

M

2009

EM

Diane

Research and Development Engineer

F

2008

EM

Gigi

Research and Development Engineer

F

2009

EM

Michael

Research and Development Manager

M

2009

EM

Ovidiu

Senior Tool Designer

M

2010

EM

Thierry

Tool Designer

M

2007

EM

Janice

Tool Designer

F

2010

EM

Michael

Senior Design Engineer

M

2010

EM

Sharon

Design Engineer

F

2011

EM

David

Marketing Manager

M

2007

EM

Kevin

Marketing Assistant

M

2007

EM

John

Marketing Specialist

M

2011

EM

Maria

Marketing Assistant

F

2011

EM

Wanida

Marketing Assistant

F

2011

Spalten mit der WITH-Anweisung auswählen

Der Body einer Inline-Funktion mit Tabellenwerten kann auch mit einer WITH -Anweisung angegeben werden, wie unten gezeigt.

Transact-SQL
Tabellenwertfunktion mit Inline-Anweisungen
CREATE FUNCTION GetMaritalStatusByGender
(
 @P_Gender nchar(1)
)

RETURNS TABLE 
AS
RETURN
(
  WITH CTE AS 
 (
  SELECT BusinessEntityID, MaritalStatus, Gender 
  FROM HumanResources.Employee 
  where Gender = @P_Gender
 ) 
  SELECT 
 MaritalStatus, Gender, CONCAT(P.FirstName,' ', P.LastName) as Name
  FROM 
 CTE INNER JOIN Person.Person P
  ON
 CTE.BusinessEntityID = P.BusinessEntityID
);

GO

select * from GetMaritalStatusByGender('F');
Copy
Ergebnis

MaritalStatus

Geschlecht

Name

S

F

Terri Duffy

M

F

Gail Erickson

S

F

Diane Margheim

M

F

Gigi Matthew

M

F

Janice Galvin

M

F

Sharon Salavaria

S

F

Mary Dempsey

M

F

Wanida Benshoof

M

F

Mary Gibson

M

F

Jill Williams

S

F

Jo Brown

M

F

Britta Simon

M

F

Margie Shoop

M

F

Rebecca Laszlo

M

F

Suchitra Mohan

M

F

Kim Abercrombie

S

F

JoLynn Dobney

M

F

Nancy Anderson

M

F

Ruth Ellerbrock

M

F

Doris Hartwig

M

F

Diane Glimp

M

F

Bonnie Kearney

M

F

Denise Smith

S

F

Diane Tibbott

M

F

Carole Poland

M

F

Carol Philips

M

F

Merav Netz

S

F

Betsy Stadick

S

F

Danielle Tiedt

S

F

Kimberly Zimmerman

M

F

Elizabeth Keyser

M

F

Mary Baker

M

F

Alice Ciccu

M

F

Linda Moschell

S

F

Angela Barbariol

S

F

Kitti Lertpiriyasuwat

S

F

Susan Eaton

S

F

Kim Ralls

M

F

Nicole Holliday

S

F

Anibal Sousa

M

F

Samantha Smith

S

F

Olinda Turner

S

F

Cynthia Randall

M

F

Sandra Reátegui Alayo

S

F

Linda Randall

S

F

Shelley Dyck

S

F

Laura Steele

S

F

Susan Metters

S

F

Katie McAskill-White

M

F

Barbara Decker

M

F

Yvonne McKay

S

F

Janeth Esteves

M

F

Brenda Diaz

M

F

Lorraine Nay

M

F

Paula Nartker

S

F

Lori Kane

M

F

Kathie Flood

S

F

Belinda Newman

M

F

Karen Berge

M

F

Lori Penor

M

F

Jo Berry

M

F

Laura Norman

M

F

Paula Barreto de Mattos

M

F

Mindy Martin

M

F

Deborah Poe

S

F

Candy Spoon

M

F

Barbara Moreland

M

F

Janet Sheperdigian

S

F

Wendy Kahn

S

F

Sheela Word

M

F

Linda Meisner

S

F

Erin Hagens

M

F

Annette Hill

S

F

Jean Trenary

S

F

Stephanie Conroy

S

F

Karen Berg

M

F

Janaina Bueno

M

F

Linda Mitchell

S

F

Jillian Carson

S

F

Pamela Ansman-Wolfe

S

F

Lynn Tsoflias

M

F

Amy Alberts

S

F

Rachel Valdez

M

F

Jae Pak

Snowflake SQL
Tabellenwertfunktion mit Inline-Anweisungen
 --** SSC-FDM-0007 - MISSING DEPENDENT OBJECTS "HumanResources.Employee", "Person.Person" **
CREATE OR REPLACE FUNCTION GetMaritalStatusByGender
(P_GENDER STRING
)
RETURNS TABLE(
 MaritalStatus STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN MaritalStatus WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
 Gender STRING /*** SSC-FDM-TS0012 - INFORMATION FOR THE COLUMN Gender WAS NOT FOUND. STRING DATATYPE USED TO MATCH CAST AS STRING OPERATION ***/,
 Name VARCHAR
)
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "07/11/2025",  "domain": "no-domain-provided" }}'
AS
$$
 --** SSC-PRF-TS0001 - PERFORMANCE WARNING - RECURSION FOR CTE NOT CHECKED. MIGHT REQUIRE RECURSIVE KEYWORD **
  WITH CTE AS
 (
  SELECT
   BusinessEntityID,
   MaritalStatus,
   Gender
  FROM
   HumanResources.Employee
  where
   Gender = :P_GENDER
 )
  SELECT
  CAST(MaritalStatus AS STRING),
  CAST(Gender AS STRING),
  CONCAT(P.FirstName,' ', P.LastName) as Name
  FROM
  CTE
  INNER JOIN
   Person.Person P
  ON CTE.BusinessEntityID = P.BusinessEntityID
$$;

select
  *
from
  TABLE(GetMaritalStatusByGender('F'));
Copy
Ergebnis

MaritalStatus

Geschlecht

Name

S

F

Terri Duffy

M

F

Gail Erickson

S

F

Diane Margheim

M

F

Gigi Matthew

M

F

Janice Galvin

M

F

Sharon Salavaria

S

F

Mary Dempsey

M

F

Wanida Benshoof

M

F

Mary Gibson

M

F

Jill Williams

S

F

Jo Brown

M

F

Britta Simon

M

F

Margie Shoop

M

F

Rebecca Laszlo

M

F

Suchitra Mohan

M

F

Kim Abercrombie

S

F

JoLynn Dobney

M

F

Nancy Anderson

M

F

Ruth Ellerbrock

M

F

Doris Hartwig

M

F

Diane Glimp

M

F

Bonnie Kearney

M

F

Denise Smith

S

F

Diane Tibbott

M

F

Carole Poland

M

F

Carol Philips

M

F

Merav Netz

S

F

Betsy Stadick

S

F

Danielle Tiedt

S

F

Kimberly Zimmerman

M

F

Elizabeth Keyser

M

F

Mary Baker

M

F

Alice Ciccu

M

F

Linda Moschell

S

F

Angela Barbariol

S

F

Kitti Lertpiriyasuwat

S

F

Susan Eaton

S

F

Kim Ralls

M

F

Nicole Holliday

S

F

Anibal Sousa

M

F

Samantha Smith

S

F

Olinda Turner

S

F

Cynthia Randall

M

F

Sandra Reátegui Alayo

S

F

Linda Randall

S

F

Shelley Dyck

S

F

Laura Steele

S

F

Susan Metters

S

F

Katie McAskill-White

M

F

Barbara Decker

M

F

Yvonne McKay

S

F

Janeth Esteves

M

F

Brenda Diaz

M

F

Lorraine Nay

M

F

Paula Nartker

S

F

Lori Kane

M

F

Kathie Flood

S

F

Belinda Newman

M

F

Karen Berge

M

F

Lori Penor

M

F

Jo Berry

M

F

Laura Norman

M

F

Paula Barreto de Mattos

M

F

Mindy Martin

M

F

Deborah Poe

S

F

Candy Spoon

M

F

Barbara Moreland

M

F

Janet Sheperdigian

S

F

Wendy Kahn

S

F

Sheela Word

M

F

Linda Meisner

S

F

Erin Hagens

M

F

Annette Hill

S

F

Jean Trenary

S

F

Stephanie Conroy

S

F

Karen Berg

M

F

Janaina Bueno

M

F

Linda Mitchell

S

F

Jillian Carson

S

F

Pamela Ansman-Wolfe

S

F

Lynn Tsoflias

M

F

Amy Alberts

S

F

Rachel Valdez

M

F

Jae Pak

Bekannte Probleme

Es wurden keine Probleme gefunden

MULTI-STATEMENT TABLE-VALUED

Übersetzungsreferenz zur Konvertierung von Transact-SQL UDF (benutzerdefinierten Funktionen) mit dem TABLE-Rückgabetyp an Snowflake.

Applies to
  • SQL Server

  • Azure Synapse Analytics

Bemerkung

Einige Teile des Ausgabecodes wurden aus Gründen der Übersichtlichkeit weggelassen.

Bemerkung

Alle Codebeispiele auf dieser Seite wurden noch nicht in SnowConvert AI implementiert. Sie sollten als Referenz dafür interpretiert werden, wie jedes Szenario in Snowflake übersetzt werden soll. Diese Übersetzungen können sich in Zukunft ändern. Einige Teile des Ausgabecodes werden aus Gründen der Übersichtlichkeit weggelassen.

Beschreibung

Eine Tabellenwertfunktion mit mehreren Anweisungen ist ähnlich wie eine Tabellenwertfunktion mit Inline-Anweisungen (INLINE TABLE-VALUED). Eine Tabellenwertfunktion mit mehreren Anweisungen kann jedoch mehr als eine Anweisung im Funktions-Body enthalten, wobei die Tabellenspalten im Rückgabetyp angegeben sind und ein BEGIN/END-Block (SQL Server-Sprachreferenz – Erstellen einer Funktion mit Tabellenwerten für mehrere Anweisungen vorhanden ist.

Transact-SQL-Syntax

CREATE [ OR ALTER ] FUNCTION [ schema_name. ] function_name
( [ { @parameter_name [ AS ] [ type_schema_name. ] parameter_data_type
    [ = default ] [READONLY] }
    [ ,...n ]
  ]
)
RETURNS @return_variable TABLE <table_type_definition>
    [ WITH <function_option> [ ,...n ] ]
    [ AS ]
    BEGIN
        function_body
        RETURN
    END
[ ; ]
Copy

Snowflake SQL

CREATE OR REPLACE FUNCTION <name> ( [ <arguments> ] )
  RETURNS TABLE ( <output_col_name> <output_col_type> [, <output_col_name> <output_col_type> ... ] )
  AS '<sql_expression>'
Copy

Beispielhafte Quellcode-Muster

Der folgende Abschnitt beschreibt alle möglichen Quellcodemuster, die in dieser Art von ofCREATE FUNCTION-Syntax auftreten können.

Der Funktions-Body einer Tabellenwertfunktion mit mehreren Anweisungen muss eine SELECT-Anweisung sein. Aus diesem Grund müssen die anderen Anweisungen separat aufgerufen werden.

Werte in eine Tabelle einfügen

Fügt eine oder mehrere Zeilen in die Tabelle ein und gibt die Tabelle mit den neuen Werten zurück

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
CREATE OR ALTER FUNCTION calc_behavioral_segment()
RETURNS @behavioral_segments TABLE (behavioral_segment VARCHAR(50))
AS
BEGIN
 DECLARE @col varchar(15)
 SET @col = 'Unknown'
 INSERT INTO @behavioral_segments 
 SELECT @col
 
 RETURN 
END

SELECT * FROM calc_behavioral_segment();
Copy
Ergebnis

BEHAVIORAL_SEGMENT

Unbekannt

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
!!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!
CREATE OR ALTER FUNCTION calc_behavioral_segment ()
RETURNS BEHAVIORAL_SEGMENTS TABLE (
 behavioral_segment VARCHAR(50))
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
BEGIN
 DECLARE @col varchar(15)
 SET @col = 'Unknown'
 INSERT INTO @behavioral_segments
 SELECT @col

 RETURN
END

SELECT * FROM calc_behavioral_segment();;
Copy
Ergebnisse

BEHAVIORAL_SEGMENT

Unbekannt

Wert entsprechend der IF/ELSE-Anweisung einfügen

Fügt entsprechend der Bedingung eine Zeile in die Tabelle ein und gibt die Tabelle mit dem neuen Wert zurück

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
CREATE OR ALTER FUNCTION odd_or_even_number(@number INT)
RETURNS @numbers TABLE (number_type VARCHAR(15))
AS
BEGIN 
 IF ((@number % 2) = 0)
 BEGIN
  INSERT @numbers SELECT 'Even'
 END
    
 ELSE
 BEGIN
  INSERT @numbers SELECT 'Odd'
 END

 RETURN
END

SELECT * FROM odd_or_even_number(9);
Copy
Ergebnis

NUMBER_TYPE

Ungerade

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
!!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!
CREATE OR ALTER FUNCTION odd_or_even_number (NUMBER INT)
RETURNS NUMBERS TABLE (
 number_type VARCHAR(15))
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
BEGIN
 IF ((@number % 2) = 0)
 BEGIN
  INSERT @numbers SELECT 'Even'
 END

 ELSE
 BEGIN
  INSERT @numbers SELECT 'Odd'
 END

 RETURN
END

SELECT * FROM odd_or_even_number(9);;
Copy
Ergebnis

NUMBER_TYPE

Ungerade

Fügt mehrere gemäß der IF/ELSE-Anweisung ein

Das folgende Beispiel fügt mehr als einen Wert in die Tabelle ein und mehr als eine Variable wird entsprechend der Bedingung geändert. Gibt die Tabelle mit den neuen Werten zurück

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
CREATE OR ALTER FUNCTION new_employee_hired(@id VARCHAR (50), @position VARCHAR(50), @experience VARCHAR(15))
RETURNS @new_employee TABLE (id_employee VARCHAR (50), working_from_home BIT, team VARCHAR(15), computer VARCHAR(15)) 
AS
BEGIN 
 DECLARE @wfh BIT
 DECLARE @team VARCHAR(15)
 DECLARE @computer VARCHAR(15)

 IF @position = 'DEVELOPER'
 BEGIN
  SET @team = 'TEAM_1'
  SET @computer = 'LAPTOP'  
 END

 IF @position = 'IT'
 BEGIN  
  SET @team = 'TEAM_2'
  SET @computer = 'DESKTOP'
 END

 IF @experience = 'JUNIOR'
 BEGIN
  SET @wfh = '0'   
 END
 IF @experience = 'SENIOR'
 BEGIN
  SET @wfh = '1'      
 END

 INSERT INTO @new_employee VALUES (@id, @wfh, @team, @computer)
 RETURN
END

SELECT * FROM new_employee_hired('123456789', 'DEVELOPER', 'SENIOR');
Copy
Ergebnis

ID_EMPLOYEE

WORKING_FROM_HOME

TEAM

COMPUTER

123456789

1

TEAM_1

LAPTOP

Snowflake
MULTI-STATEMENT TABLE-VALUED
 !!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!
CREATE OR ALTER FUNCTION new_employee_hired (ID STRING, POSITION STRING, EXPERIENCE STRING)
RETURNS NEW_EMPLOYEE TABLE (
 id_employee VARCHAR(50),
 working_from_home BOOLEAN,
 team VARCHAR(15),
 computer VARCHAR(15))
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
BEGIN
 DECLARE @wfh BIT
 DECLARE @team VARCHAR(15)
 DECLARE @computer VARCHAR(15)

 IF @position = 'DEVELOPER'
 BEGIN
  SET @team = 'TEAM_1'
  SET @computer = 'LAPTOP'
 END

 IF @position = 'IT'
 BEGIN
  SET @team = 'TEAM_2'
  SET @computer = 'DESKTOP'
 END

 IF @experience = 'JUNIOR'
 BEGIN
  SET @wfh = '0'
 END
 IF @experience = 'SENIOR'
 BEGIN
  SET @wfh = '1'
 END

 INSERT INTO @new_employee VALUES (@id, @wfh, @team, @computer)
 RETURN
END

SELECT * FROM new_employee_hired('123456789', 'DEVELOPER', 'SENIOR');;
Copy
Ergebnis

ID_EMPLOYEE

WORKING_FROM_HOME

TEAM

COMPUTER

123456789

1

TEAM_1

LAPTOP

Warnung

Falls es verschachtelte IF-Anweisungen gibt und mehr als eine Variable in den Anweisungen geändert wird, ist es notwendig, eine gespeicherte Prozedur zu verwenden.

Zuvor eingefügte Werte aktualisieren

Aktualisiert die Spaltenwerte der Tabelle im Funktions-Body und gibt ihn mit den neuen Werten zurück.

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
CREATE OR ALTER FUNCTION get_employees_history()
RETURNS @employee_history TABLE (
 department_name NVARCHAR(50),
 first_name NVARCHAR(50),
 last_name NVARCHAR(50), 
 start_date DATE,
 end_date DATE,
 job_title NVARCHAR(50), 
 months_working INT
)
BEGIN
 INSERT INTO @employee_history
 SELECT D.name AS department_name, P.first_name, P.last_name, EH.start_date, EH.end_date, E.job_title, 0 FROM Department D
 LEFT OUTER JOIN employee_department_history EH
  ON D.department_ID = EH.department_ID
 INNER JOIN  Employee E
  ON E.business_entity_ID = EH.business_entity_ID
 INNER JOIN Person P
  ON P.business_entity_ID = E.business_entity_ID 
  

 UPDATE @employee_history
 SET 
  months_working = 
  CASE WHEN end_date IS NULL THEN DATEDIFF(MONTH, start_date, GETDATE())
  ELSE DATEDIFF(MONTH, start_date, end_date)
 END
 RETURN;
END;

SELECT TOP(10) * FROM get_employees_history();
Copy
Ergebnis

DEPARTMENT_NAME

FIRST_NAME

LAST_NAME

START_DATE

END_DATE

JOB_TITLE

MONTHS_WORKING

Sales

Syed

Abbas

2013-03-14

NULL

Pacific Sales Manager

106

Produktion

Kim

Abercrombie

2010-01-16

NULL

Production Technician – WC60

144

Quality Assurance

Hazem

Abolrous

2009-02-28

NULL

Quality Assurance Manager

155

Shipping and Receiving

Pilar

Ackerman

2009-01-02

NULL

Shipping and Receiving Supervisor

156

Produktion

Jay

Adams

2009-03-05

NULL

Production Technician – WC60

154

Information Services

François

Ajenstat

2009-01-17

NULL

Database Administrator

156

Sales

Amy

Alberts

2012-04-16

NULL

European Sales Manager

117

Produktion

Greg

Alderson

2008-12-02

NULL

Production Technician – WC45

157

Quality Assurance

Sean

Alexander

2008-12-28

NULL

Quality Assurance Technician

157

Facilities and Maintenance

Gary

Altman

2009-12-02

NULL

Facilities Manager

145

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
!!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!
CREATE OR ALTER FUNCTION get_employees_history ()
RETURNS EMPLOYEE_HISTORY TABLE (
 department_name VARCHAR(50),
 first_name VARCHAR(50),
 last_name VARCHAR(50),
 start_date DATE,
 end_date DATE,
 job_title VARCHAR(50),
 months_working INT
)
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
BEGIN
 INSERT INTO @employee_history
 SELECT D.name AS department_name, P.first_name, P.last_name, EH.start_date, EH.end_date, E.job_title, 0 FROM Department D
 LEFT OUTER JOIN employee_department_history EH
  ON D.department_ID = EH.department_ID
 INNER JOIN  Employee E
  ON E.business_entity_ID = EH.business_entity_ID
 INNER JOIN Person P
  ON P.business_entity_ID = E.business_entity_ID


 UPDATE @employee_history
 SET
  months_working =
  CASE WHEN end_date IS NULL THEN DATEDIFF(MONTH, start_date, GETDATE())
  ELSE DATEDIFF(MONTH, start_date, end_date)
 END
 RETURN;
END;

SELECT TOP(10) * FROM get_employees_history();;
Copy
Ergebnis

DEPARTMENT_NAME

FIRST_NAME

LAST_NAME

START_DATE

END_DATE

JOB_TITLE

MONTHS_WORKING

Sales

Syed

Abbas

2013-03-14

NULL

Pacific Sales Manager

106

Produktion

Kim

Abercrombie

2010-01-16

NULL

Production Technician – WC60

144

Quality Assurance

Hazem

Abolrous

2009-02-28

NULL

Quality Assurance Manager

155

Shipping and Receiving

Pilar

Ackerman

2009-01-02

NULL

Shipping and Receiving Supervisor

156

Produktion

Jay

Adams

2009-03-05

NULL

Production Technician – WC60

154

Information Services

François

Ajenstat

2009-01-17

NULL

Database Administrator

156

Sales

Amy

Alberts

2012-04-16

NULL

European Sales Manager

117

Produktion

Greg

Alderson

2008-12-02

NULL

Production Technician – WC45

157

Quality Assurance

Sean

Alexander

2008-12-28

NULL

Quality Assurance Technician

157

Facilities and Maintenance

Gary

Altman

2009-12-02

NULL

Facilities Manager

145

Mehrere RETURN-Klauseln

Im folgenden Beispiel gibt es mehr als eine Klausel, da es je nach Situation nicht notwendig ist, die gesamte Funktion auszuführen.

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
CREATE OR ALTER FUNCTIONcreate_new_team(@team_name VARCHAR(50))
</strong>RETURNS @new_team TABLE (type VARCHAR(50), name VARCHAR(50))
AS
BEGIN
 DECLARE @employees INT
 SET @employees = (SELECT count(*) FROM employee)
 DECLARE @type VARCHAR(15)
 SET @type = 'small_team'
 IF (@employees &#x3C; 8)
 BEGIN
  INSERT @new_team VALUES (@type, @team_name)
  RETURN
 END

 SET @type = 'big_team'
 INSERT @new_team VALUES (@type, @team_name)

 RETURN
END

SELECT * FROMcreate_new_team('Team1');
Copy
Ergebnis

TYPE

NAME

SMALL_TEAM

TEAM1

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
!!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!
CREATE OR ALTER FUNCTIONcreate_new_team (TEAM_NAME STRING)
RETURNS NEW_TEAM TABLE (
 type VARCHAR(50),
 name VARCHAR(50))
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
BEGIN
 DECLARE @employees INT
 SET @employees = (SELECT count(*) FROM employee)
 DECLARE @type VARCHAR(15)
 SET @type = 'small_team'
 IF (@employees < 8)
 BEGIN
  INSERT @new_team VALUES (@type, @team_name)
  RETURN
 END

 SET @type = 'big_team'
 INSERT @new_team VALUES (@type, @team_name)

 RETURN
END

SELECT * FROMcreate_new_team('Team1');;
Copy
Ergebnis

TYPE

NAME

SMALL_TEAM

TEAM1

Warnung

Diese Transformation wird angewendet, wenn nur ein Wert eingefügt werden soll. Bei mehr als einem Wert müssen Sie eine gespeicherte Prozedur verwenden.

Komplexe Fälle

Das Beispiel ist ein komplexer Fall, der verschachtelte if-Anweisungen verwendet und einen Wert abhängig von der Bedingung „true“ einfügt.

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
CREATE OR ALTER FUNCTION vacation_status(@id VARCHAR (50))
RETURNS @status TABLE (vacation_status VARCHAR(30))
AS
BEGIN 
 DECLARE @hire_date DATETIME
 SET @hire_date = (SELECT @hire_date FROM employee WHERE employeeId = @id)
 DECLARE @vacation_hours INT
 SET @vacation_hours = (SELECT count(vacation_hours) FROM employee WHERE employeeId = @id)
 DECLARE @time_working INT
 SET @time_working = (SELECT DATEDIFF(MONTH, @hire_date,GETDATE()))

 IF (@vacation_hours > 0)
 BEGIN
  IF (@time_working > 3)
  BEGIN
   IF (@vacation_hours < 120)
   BEGIN
    INSERT INTO @status VALUES ('Ok')
   END

   IF (@vacation_hours = 120)
   BEGIN
    INSERT INTO @status values ('In the limit')
   END

   IF (@vacation_hours > 120)
   BEGIN
    INSERT INTO @status VALUES ('With excess')
   END
  END
  ELSE
  BEGIN
   INSERT INTO @status values ('Hired recently')
  END
 END
 ELSE
 BEGIN
  INSERT INTO @status values ('No hours')
 END
 RETURN
END

SELECT * FROM vacation_status('adventure-worksken0')
Copy
Ergebnis

VACATION_STATUS

OK

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
 !!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!
CREATE OR ALTER FUNCTION vacation_status (ID STRING)
RETURNS STATUS TABLE (
 vacation_status VARCHAR(30))
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
BEGIN
 DECLARE @hire_date DATETIME
 SET @hire_date = (SELECT @hire_date FROM employee WHERE employeeId = @id)
 DECLARE @vacation_hours INT
 SET @vacation_hours = (SELECT count(vacation_hours) FROM employee WHERE employeeId = @id)
 DECLARE @time_working INT
 SET @time_working = (SELECT DATEDIFF(MONTH, @hire_date,GETDATE()))

 IF (@vacation_hours > 0)
 BEGIN
  IF (@time_working > 3)
  BEGIN
   IF (@vacation_hours < 120)
   BEGIN
    INSERT INTO @status VALUES ('Ok')
   END

   IF (@vacation_hours = 120)
   BEGIN
    INSERT INTO @status values ('In the limit')
   END

   IF (@vacation_hours > 120)
   BEGIN
    INSERT INTO @status VALUES ('With excess')
   END
  END
  ELSE
  BEGIN
   INSERT INTO @status values ('Hired recently')
  END
 END
 ELSE
 BEGIN
  INSERT INTO @status values ('No hours')
 END
 RETURN
END

SELECT * FROM vacation_status('adventure-worksken0');
Copy
Zweiter Tab

VACATION_STATUS

OK

Bekannte Probleme

WHILE-Anweisungen in Verbindung mit Abfragen

Das Problem bei diesem Beispiel ist, dass es keine Möglichkeit gibt, die WHILE-Anweisung innerhalb der WITH-Klausel des Haupt-Select in eine CTE umzuwandeln. Dadurch sind wir gezwungen, diese Anweisung in eine gespeicherte Prozedur umzuwandeln, um die gleiche Logik zu erhalten.

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
--Additional Params: -t JavaScript
CREATE OR ALTER FUNCTION get_group_name
(@department_id INT)
RETURNS @group_names TABLE (group_name VARCHAR(15))
AS
BEGIN
DECLARE @name VARCHAR(30) = 'Another Department'  
WHILE @name = 'Another Department'
BEGIN
 IF (@department_id &#x3C; 3)
 BEGIN
  SET @name = 'engineering'
 END

 IF @department_id = 3
 BEGIN
  SET @name = 'Tool Design'
 END

 SELECT @department_id = @department_id / 3
END
INSERT @group_names SELECT @name
RETURN
END

SELECT * FROM get_group_name(9);
Copy
Ergebnis

GROUP_NAME

Tool Design

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
 !!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!
CREATE OR ALTER FUNCTION get_group_name
(DEPARTMENT_ID INT)
RETURNS @group_names TABLE (
 group_name VARCHAR(15))
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
BEGIN
DECLARE @name VARCHAR(30) = 'Another Department'
WHILE @name = 'Another Department'
BEGIN
 IF (@department_id < 3)
 BEGIN
  SET @name = 'engineering'
 END

 IF @department_id = 3
 BEGIN
  SET @name = 'Tool Design'
 END

 SELECT @department_id = @department_id / 3
END
INSERT @group_names SELECT @name
RETURN
END

SELECT * FROM get_group_name(9);;
Copy
Ergebnis

GROUP_NAME

Tool Design

Cursor deklarieren

Benutzerdefinierte Funktionen können DECLARE, OPEN, FETCH, CLOSE oder DEALLOCATE für einen CURSOR nicht verwenden. Verwenden Sie eine gespeicherte Prozedur, um mit Cursors zu arbeiten.

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
 --Additional Params: -t JavaScript

CREATE OR ALTER FUNCTION amount_new_specimens(@id int)
RETURNS @new_specimens TABLE (amount int)
AS
BEGIN
 DECLARE @first_specimen VARCHAR(30) ;
 set @first_specimen = (select name_specimen from specimen where specimen_id = @id);
 DECLARE @second_specimen VARCHAR(30);

 DECLARE @specimens TABLE (name_specimen VARCHAR(30))

 DECLARE Cursor1 CURSOR 
 FOR SELECT name_specimen 
 FROM specimen 

 OPEN cursor1
 FETCH NEXT FROM cursor1
 INTO @second_specimen;
 
 WHILE @@FETCH_STATUS = 0 
 BEGIN
  IF @first_specimen <> @second_specimen
  BEGIN
   INSERT INTO @specimens values (CONCAT_WS('-', @first_specimen, @second_specimen))
  END
  FETCH NEXT FROM cursor1
  INTO @second_specimen;
 END

 CLOSE cursor1;
 DEALLOCATE cursor1;

 INSERT INTO @new_specimens SELECT COUNT(*) FROM @specimens
 RETURN 
END

SELECT * FROM amount_new_specimens(1);
Copy
Ergebnis

AMOUNT

3

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
 --Additional Params: -t JavaScript
!!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'TABLE VALUED FUNCTIONS' NODE ***/!!!

CREATE OR ALTER FUNCTION amount_new_specimens (ID INT)
RETURNS @new_specimens TABLE (
 amount INT
)
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
BEGIN
 DECLARE @first_specimen VARCHAR(30) ;
 set @first_specimen = (select name_specimen from specimen where specimen_id = @id);
 DECLARE @second_specimen VARCHAR(30);

 DECLARE @specimens TABLE (name_specimen VARCHAR(30))

 DECLARE Cursor1 CURSOR
 FOR SELECT name_specimen
 FROM specimen

 OPEN cursor1
 FETCH NEXT FROM cursor1
 INTO @second_specimen;

 WHILE @@FETCH_STATUS = 0
 BEGIN
  IF @first_specimen <> @second_specimen
  BEGIN
   INSERT INTO @specimens values (CONCAT_WS('-', @first_specimen, @second_specimen))
  END
  FETCH NEXT FROM cursor1
  INTO @second_specimen;
 END

 CLOSE cursor1;
 DEALLOCATE cursor1;

 INSERT INTO @new_specimens SELECT COUNT(*) FROM @specimens
 RETURN
END

SELECT * FROM amount_new_specimens(1);;
Copy
Ergebnis

AMOUNT

3

Verschiedene Anweisungen werden in allgemeinen Tabellenausdrücken nicht unterstützt

Die Klauseln UPDATE, INSERT, DELETE, ALTER oder DROP werden im Body von allgemeinen Tabellenausdrücken nicht unterstützt, auch nicht nach ihrer Deklaration mit einem Delimitator. Aus diesem Grund kann die Funktion so geändert werden, dass sie als gespeicherte Prozedur funktioniert.

Transact-SQL
MULTI-STATEMENT TABLE-VALUED
 --Additional Params: -t JavaScript

CREATE OR ALTER PROCEDURE product_history 
AS
BEGIN
 DECLARE @product_history TABLE (
  product_name NVARCHAR(50),
  rating INT
 )
 INSERT INTO @product_history
 SELECT P.Name AS product_name, AVG(ALL R.rating) FROM Production.product P
 INNER JOIN  Production.product_review R
  ON R.product_ID = P.product_ID
 GROUP BY P.Name;

 DELETE FROM @product_history
 WHERE rating < 2;

 SELECT * FROM @product_history; 

END
GO;

EXEC product_history
Copy
Ergebnis

PRODUCT_NAME

Bewertung

HL Mountain Pedal

3

Mountain Bike Socks, M

5

Road-550-W Yellow, 40

5

Snowflake SQL
MULTI-STATEMENT TABLE-VALUED
CREATE OR REPLACE PROCEDURE product_history ()
RETURNS STRING
LANGUAGE JAVASCRIPT
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},{"attributes":{"component":"transact"}}'
EXECUTE AS CALLER
AS
$$
 // REGION SnowConvert AI Helpers Code
 var _RS, ROW_COUNT, _ROWS, MESSAGE_TEXT, SQLCODE = 0, SQLSTATE = '00000', OBJECT_SCHEMA_NAME  = 'UNKNOWN', ERROR_HANDLERS, NUM_ROWS_AFFECTED, PROC_NAME = arguments.callee.name, DOLLAR_DOLLAR = '$' + '$';
 function* sqlsplit(sql) {
  var part = '';
  var ismark = () => sql[i] == '$' && sql[i + 1] == '$';
  for(var i = 0;i < sql.length;i++) {
   if (sql[i] == ';') {
    yield part + sql[i];
    part = '';
   } else if (ismark()) {
    part += sql[i++] + sql[i++];
    while ( i < sql.length && !ismark() ) {
     part += sql[i++];
    }
    part += sql[i] + sql[i++];
   } else part += sql[i];
  }
  if (part.trim().length) yield part;
 };
 var formatDate = (arg) => (new Date(arg - (arg.getTimezoneOffset() * 60000))).toISOString().slice(0,-1);
 var fixBind = function (arg) {
  arg = arg == undefined ? null : arg instanceof Date ? formatDate(arg) : arg;
  return arg;
 };
 var EXEC = (stmt,binds = [],severity = "16",noCatch = false) => {
  binds = binds ? binds.map(fixBind) : binds;
  for(var stmt of sqlsplit(stmt)) {
   try {
    _RS = snowflake.createStatement({
      sqlText : stmt,
      binds : binds
     });
    _ROWS = _RS.execute();
    ROW_COUNT = _RS.getRowCount();
    NUM_ROWS_AFFECTED = _RS.getNumRowsAffected();
    return {
     THEN : (action) => !SQLCODE && action(fetch(_ROWS))
    };
   } catch(error) {
    let rStack = new RegExp('At .*, line (\\d+) position (\\d+)');
    let stackLine = error.stackTraceTxt.match(rStack) || [0,-1];
    MESSAGE_TEXT = error.message.toString();
    SQLCODE = error.code.toString();
    SQLSTATE = error.state.toString();
    snowflake.execute({
     sqlText : `SELECT UPDATE_ERROR_VARS_UDF(?,?,?,?,?,?)`,
     binds : [stackLine[1],SQLCODE,SQLSTATE,MESSAGE_TEXT,PROC_NAME,severity]
    });
    throw error;
   }
  }
 };
 // END REGION

  EXEC(`CREATE OR REPLACE TEMPORARY TABLE T_product_history (
   product_name VARCHAR(50),
   rating INT
)`);
 EXEC(` INSERT INTO T_product_history
 SELECT
    P.Name AS product_name,
    AVG(ALL R.rating) FROM
    Production.product P
    INNER JOIN
       Production.product_review R
       ON R.product_ID = P.product_ID
 GROUP BY
    P.Name`);
 EXEC(`DELETE FROM
   T_product_history
WHERE
   rating < 2`);
 EXEC(`
 SELECT
    *
 FROM
    T_product_history`);
$$;
;

CALL product_history();
Copy
Ergebnis

PRODUCT_NAME

Bewertung

HL Mountain Pedal

3

Mountain Bike Socks, M

5

Road-550-W Yellow, 40

5

Zugehörige EWIs

  1. SSC-EWI-0040: Anweisung nicht unterstützt.#x20;

  2. [SSC-EWI-0073](../../general/technical-documentation/issues-and-troubleshooting/conversion-issues/generalEWI. md#ssc-ewi-0073): Überprüfung der Funktionsäquivalenz ausstehend

SCALAR

Übersetzungsreferenz zur Konvertierung von Transact-SQL UDF (benutzerdefinierten Funktionen) mit dem „scalar“-Rückgabetyp an Snowflake.

Applies to
  • SQL Server

  • Azure Synapse Analytics

Beschreibung

Bemerkung

Einige Teile des Ausgabecodes wurden aus Gründen der Übersichtlichkeit weggelassen.

Eine benutzerdefinierte Skalarfunktion ist eine Transact-SQL- oder Common Language Runtime(CLR)-Routine, die Parameter akzeptiert, eine Aktion ausführt, z. B. eine komplexe Berechnung, und das Ergebnis dieser Aktion als Skalarwert zurückgibt. (SQL Server-Sprachreferenz – Unterabschnitt ReferenceCREATE FUNCTION).

Bemerkung

Diese Funktionen werden in der Regel innerhalb der Anweisung SELECToder bei der Einrichtung einer einzelnen Variablen (höchstwahrscheinlich innerhalb einer gespeicherten Prozedur) verwendet.

Transact-SQL-Syntax

 -- Transact-SQL Scalar Function Syntax
CREATE [ OR ALTER ] FUNCTION [ schema_name. ] function_name
( [ { @parameter_name [ AS ][ type_schema_name. ] parameter_data_type
 [ = default ] [ READONLY ] }
    [ ,...n ]
  ]
)
RETURNS return_data_type
    [ WITH <function_option> [ ,...n ] ]
    [ AS ]
    BEGIN
        function_body
        RETURN scalar_expression
    END
[ ; ]
Copy

Snowflake-Syntax

Snowflake erlaubt 3 verschiedene Sprachen in den benutzerdefinierten Funktionen:

  • SQL

  • JavaScript

  • Java

Vorerst unterstützt SnowConvert AI nur SQL und JavaScript als Zielsprachen.

SQL

Bemerkung

Benutzerdefinierte SQL-Funktionen unterstützen nur eine Abfrage als Body. Sie können aus der Datenbank lesen, aber nicht schreiben oder verändern. (Referenz zu skalaren SQL UDFs).

CREATE [ OR REPLACE ] [ SECURE ] FUNCTION <name> ( [ <arg_name> <arg_data_type> ] [ , ... ] )
  RETURNS { <result_data_type> | TABLE ( <col_name> <col_data_type> [ , ... ] ) }
  [ [ NOT ] NULL ]
  [ { CALLED ON NULL INPUT | { RETURNS NULL ON NULL INPUT | STRICT } } ]
  [ VOLATILE | IMMUTABLE ]
  [ COMMENT = '<string_literal>' ]
  AS '<function_definition>'
Copy
JavaScript

Bemerkung

Benutzerdefinierte JavaScript-Funktionen erlauben mehrere Anweisungen in ihren Bodys, können aber keine Abfragen an die Datenbank durchführen. (Referenz zu skalaren JavaScript UDFs)

CREATE [ OR REPLACE ] [ SECURE ] FUNCTION <name> ( [ <arg_name> <arg_data_type> ] [ , ... ] )
  RETURNS { <result_data_type> | TABLE ( <col_name> <col_data_type> [ , ... ] ) }
  [ [ NOT ] NULL ]
  LANGUAGE JAVASCRIPT
  [ { CALLED ON NULL INPUT | { RETURNS NULL ON NULL INPUT | STRICT } } ]
  [ VOLATILE | IMMUTABLE ]
  [ COMMENT = '<string_literal>' ]
  AS '<function_definition>'
Copy

Beispielhafte Quellcode-Muster

SET- und DECLARE-Anweisungen

Die häufigsten Anweisungen in Funktions-Bodys sind die Anweisungen DECLARE und SET. Bei DECLARE-Anweisungen ohne Standardwert wird die Transformation ignoriert. SET-Anweisungen und DECLARE-Anweisungen mit einem Standardwert werden in COMMON TABLE EXPRESSION umgewandelt. Jeder gemeinsame Tabellenausdruck enthält eine Spalte, die den Wert der lokalen Variablen darstellt.

Transact-SQL
Abfrage
CREATE OR ALTER FUNCTION PURCHASING.GetVendorName()
RETURNS NVARCHAR(50) AS
BEGIN
 DECLARE @result NVARCHAR(50)
 DECLARE @BUSINESSENTITYID INT
 
 SET @BUSINESSENTITYID = 1492
 
 SELECT @result = Name FROM PURCHASING.VENDOR WHERE BUSINESSENTITYID = @BUSINESSENTITYID
 
 RETURN @result
END

GO

SELECT PURCHASING.GetVendorName() as vendor_name;
Copy
Ergebnis

vendor_name

Australia Bike Retailer

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION PURCHASING.GetVendorName ()
RETURNS VARCHAR(50)
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
 WITH CTE1 AS
 (
  SELECT
   1492 AS BUSINESSENTITYID
 ),
 CTE2 AS
 (
  SELECT
   Name AS RESULT
  FROM
   PURCHASING.VENDOR
  WHERE
   BUSINESSENTITYID = (
    SELECT
     BUSINESSENTITYID
    FROM
     CTE1
   )
 )
 SELECT
  RESULT
 FROM
  CTE2
$$;

SELECT
 PURCHASING.GetVendorName() as vendor_name;
Copy
Ergebnis

VENDOR_NAME

Australia Bike Retailer

Transformation von IF/ELSE-Anweisung

IF/ELSE-Anweisungen können auf unterschiedliche Weise gehandhabt werden. Sie können entweder in Javascript oder in SQL transformiert werden, indem die CASE EXPRESSION innerhalb der SELECT-Anweisung die Bedingungen innerhalb der Abfragen zulässt. Während die Transformation in Javascript ziemlich einfach ist, ist die CASE-Anweisung auf den ersten Blick vielleicht nicht so offensichtlich.

Transact-SQL
Abfrage
CREATE OR ALTER FUNCTION PURCHASING.HasActiveFlag(@BusinessEntityID int)
RETURNS VARCHAR(10) AS
BEGIN
 DECLARE @result VARCHAR(10)
 DECLARE @ActiveFlag BIT
 
 SELECT @ActiveFlag = ActiveFlag from PURCHASING.VENDOR v where v.BUSINESSENTITYID = @BusinessEntityID
 
 IF @ActiveFlag = 1
  SET @result = 'YES'
 ELSE IF @ActiveFlag = 0 
  SET @result = 'NO'
 
 RETURN @result
END

GO

SELECT PURCHASING.HasActiveFlag(1516) as has_active_flag;
Copy
Ergebnis

has_active_flag

NO

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION PURCHASING.HasActiveFlag (P_BUSINESSENTITYID INT)
RETURNS VARCHAR(10)
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
 WITH CTE1 AS
 (

  SELECT
   ActiveFlag AS ACTIVEFLAG
  from
   PURCHASING.VENDOR v
  where
   v.BUSINESSENTITYID = P_BUSINESSENTITYID
 ),
 CTE2 AS
 (
  SELECT
   CASE
    WHEN (
     SELECT
      ACTIVEFLAG
     FROM
      CTE1
    ) = 1
     THEN 'YES'
    WHEN (
     SELECT
      ACTIVEFLAG
     FROM
      CTE1
    ) = 0
     THEN 'NO'
   END AS RESULT
 )
 SELECT
  RESULT
 FROM
  CTE2
$$;

SELECT
 PURCHASING.HasActiveFlag(1516) as has_active_flag;
Copy
Ergebnis

HAS_ACTIVE_FLAG

NO

NESTED-Anweisungen

Bei NESTED-Anweisungen wird die strukturierte Programmierung in eine einzige Abfrage umgewandelt. Die Anweisungen in der Ablaufsteuerung werden in Tabellenstrukturen verschachtelt, um die Ausführungsreihenfolge beizubehalten.

Bemerkung

CASE EXPRESSIONS kann nur einen Wert pro Anweisung zurückgeben

Beispiel

Bemerkung

Der folgende Code ist in beiden Programmierparadigmen funktional gleichwertig.

Strukturierte Programmierung
 DECLARE @VendorId AS int;
DECLARE @AccountNumber AS VARCHAR(50);
SELECT @VendorId = poh.VendorID 
    FROM Purchasing.PurchaseOrderHeader poh
    WHERE PurchaseOrderID = 1
SELECT @AccountNumber = v.AccountNumber
    FROM Purchasing.Vendor v
    WHERE v.BusinessEntityID = @VendorId
Copy
SQL
 SELECT V.AccountNumber AccountNumber
FROM (SELECT poh.VendorID VendorId 
         FROM Purchasing.PurchaseOrderHeader poh
         WHERE PurchaseOrderID = 1
) T1, Purchasing.Vendor v
WHERE v.BusinessEntityID = T1.VendorId
Copy
Ergebnis

AccountNumber

LITWARE0001

Bedingte Variablen durch SELECTs

Die Definition und Zuweisung von Variablen innerhalb von bedingten Anweisungen ist tendenziell etwas problematisch, da Verweise auf die Variable weiter unten im Code wissen müssten, wo die Variable zuletzt geändert wurde. Und nicht nur das: Wenn der Verweis innerhalb einer anderen bedingten Anweisung steht, müsste es eine Art Umleitung geben, die auf die vorherige bekannte Zuweisung an die Variable verweist.

Verschärft wird dies alles noch durch Verschachtelungen und komplexe Abfragen im Eingabecode. Aus diesem Grund wird ein bestimmter EWI hinzugefügt, wenn diese Muster gefunden werden.

Im folgenden Szenario kann die erste IF-Anweisung ohne Probleme umgewandelt werden, da der Inhalt einfach genug ist. Die zweite und dritte IF-Anweisung sind auskommentiert, weil sie derzeit nicht unterstützt werden, da es andere Anweisungen als Variablenzuweisungen durch SELECT gibt.

SQL Server
Abfrage
CREATE or ALTER FUNCTION PURCHASING.SELECTINUDF (
    @param1 varchar(12)
)
RETURNS int
AS
BEGIN
    declare @var1 int;
    declare @var2 int;
    declare @var3 int;

    IF @param1 = 'first'
    BEGIN
        select @var1 = col1 + 10 from table1 WHERE id = 0;
        select @var2 = col1 + 20 from table1 WHERE id = 0;
        select @var3 = col1 + 30 from table1 WHERE id = 0;
    END

    IF @param1 = 'second'
    BEGIN
        declare @var4 int = 10;
        select @var1 = col1 + 40 from table1 WHERE id = 0;
        select @var2 = col1 + 40 from table1 WHERE id = 0;
    END

    IF @param1 = 'third'
    BEGIN
        select col1 from table1 where id = 0;
        select @var1 = col1 + 50 from table1 WHERE id = 0;
        select @var2 = col1 + 50 from table1 WHERE id = 0;
    END

    RETURN @var1
END

SELECT PURCHASING.SELECTINUDF('first') as result; -- Assuming table1.col1 is 0 when ID = 0
Copy
Ergebnis

RESULT

10

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION PURCHASING.SELECTINUDF (PARAM1 STRING)
RETURNS INT
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
    WITH CTE1 AS
    (
        SELECT
            CASE
                WHEN PARAM1 = 'first'
                    THEN (SELECT
                        col1 + 10 AS VAR1 from
                        table1
                        WHERE
                        id = 0)
            END AS VAR1,
            CASE
                WHEN PARAM1 = 'first'
                        THEN (SELECT
                        col1 + 20 AS VAR2 from
                        table1
                        WHERE
                        id = 0)
            END AS VAR2,
            CASE
                WHEN PARAM1 = 'first'
                        THEN (SELECT
                        col1 + 30 AS VAR3 from
                        table1
                        WHERE
                        id = 0)
            END AS VAR3
    ),
    !!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'IF STATEMENT' NODE ***/!!!
    CTE2 AS
    (
        /*    IF @param1 = 'second'
            BEGIN
                declare @var4 int = 10;
                select @var1 = col1 + 40 from table1 WHERE id = 0;
                select @var2 = col1 + 40 from table1 WHERE id = 0;
            END*/
        SELECT
            null
    ),
    !!!RESOLVE EWI!!! /*** SSC-EWI-0073 - PENDING FUNCTIONAL EQUIVALENCE REVIEW FOR 'IF STATEMENT' NODE ***/!!!
    CTE3 AS
    (
        /*    IF @param1 = 'third'
            BEGIN
                select col1 from table1 where id = 0;
                select @var1 = col1 + 50 from table1 WHERE id = 0;
                select @var2 = col1 + 50 from table1 WHERE id = 0;
            END*/
        SELECT
            null
    ),
    CTE4 AS
    (

        SELECT
            PURCHASING.SELECTINUDF('first') as result
    )
    SELECT
        VAR1
    FROM
        CTE4
$$ -- Assuming table1.col1 is 0 when ID = 0
;
Copy
Ergebnis

RESULT

10

Eine Variable zuweisen und zurückgeben

In diesem einfachen Muster gibt es eine Variablendeklaration, dann wird diese Variable mit einer SELECT-Anweisung gesetzt und schließlich zurückgegeben. Diese wird in einen allgemeinen Tabellenausdruck umgewandelt, um die ursprüngliche Verhaltensweise beizubehalten.

SQL Server
Abfrage
CREATE OR ALTER FUNCTION Purchasing.GetTotalFreight()
RETURNS MONEY AS
BEGIN
 DECLARE @Result MONEY
 SELECT @Result = ISNULL(SUM(t.Freight), 0) from Purchasing.PurchaseOrderHeader t
 return @Result
END

GO

select Purchasing.GetTotalFreight() as Result;
Copy
Ergebnis

Ergebnis

1583978.2263

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION Purchasing.GetTotalFreight ()
RETURNS NUMBER(38, 4)
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
 WITH CTE1 AS
 (
  SELECT
   NVL(SUM(t.Freight), 0) AS RESULT from
   Purchasing.PurchaseOrderHeader t
 )
 SELECT
  RESULT
 FROM
  CTE1
$$;

select
 Purchasing.GetTotalFreight() as Result;
Copy
Ergebnis

RESULT

1583978.2263

Aufrufe mehrerer Funktionen

Für dieses spezielle Muster gibt es keine offensichtlichen Abfragen, aber es gibt mehrere Aufrufe mehrerer Funktionen, die mit derselben Variable arbeiten und sie am Ende zurückgeben. Da Snowflake nur Abfragen innerhalb seiner Funktionen unterstützt, besteht die Lösung für diesen Block darin, ihn zu einem Select hinzuzufügen und die Aufrufe darin zu verschachteln, wobei sicherzustellen ist, dass der Rückgabewert mit dem der Quelle übereinstimmt.

SQL Server
Abfrage
CREATE OR ALTER FUNCTION PURCHASING.Foo
(
 @PARAM1 INT
)
RETURNS varchar(25)
AS
BEGIN
 DECLARE @filter INT = @PARAM1
 DECLARE @NAME VARCHAR(25) = (SELECT Name from Purchasing.Vendor v where BusinessEntityID = @filter) 
 SET @NAME = REPLACE(@NAME, 'Australia', 'USA')
 SET @NAME = REPLACE(@NAME, 'Bike', 'Car')
 RETURN @NAME
END

GO

SELECT PURCHASING.Foo(1492) AS Name;
Copy
Ergebnis

Name

USA Car Retailer

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION PURCHASING.Foo (PARAM1 INT)
RETURNS VARCHAR(25)
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
 WITH CTE1 AS
 (
  SELECT
   PARAM1 AS FILTER
 ),
 CTE2 AS
 (
  SELECT
   (SELECT
     Name
    from
     Purchasing.Vendor v
    where
     BusinessEntityID = (
      SELECT
       FILTER
      FROM
       CTE1
     )
   ) AS NAME
 ),
 CTE3 AS
 (
  SELECT
   REPLACE((
    SELECT
     NAME
    FROM
     CTE3
   ), 'Australia', 'USA') AS NAME
 ),
 CTE4 AS
 (
  SELECT
   REPLACE((
    SELECT
     NAME
    FROM
     CTE4
   ), 'Bike', 'Car') AS NAME
 )
 SELECT
  NAME
 FROM
  CTE4
$$;

SELECT
 PURCHASING.Foo(1492) AS Name;
Copy
Ergebnis

NAME

USA Car Retailer

Eine Variable basierend auf mehreren IF Bedingungen erhöhen und ihren Wert zurückgeben

Bei diesem Muster wird eine Variable durch mehrere IF-Bedingungen verändert (in diesem Fall erhöht). Zu Beginn wird ein Satz von Variablen initialisiert und verwendet, um zu bestimmen, ob die Ergebnisvariable erhöht werden soll oder nicht. Schließlich wird die Ergebnisvariable zurückgegeben.

SQL Server
Abfrage
CREATE OR ALTER FUNCTION PURCHASING.FOO() 
RETURNS MONEY
AS
BEGIN
 declare @firstValue MONEY
 declare @secondValue MONEY
 declare @Result MONEY
 select  @Result = 0
 select  @firstValue = SubTotal from Purchasing.PurchaseOrderHeader where PurchaseOrderID = 1
 select  @secondValue = SubTotal from Purchasing.PurchaseOrderHeader where PurchaseOrderID = 2
 if @firstValue is not null
  select @Result = @Result + @firstValue
 if @secondValue is not null
  select @Result = @Result + @secondValue
 return @Result 
END

GO

SELECT PURCHASING.Foo() AS Result;
Copy
Ergebnis

Ergebnis

473.1415

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION PURCHASING.FOO ()
RETURNS NUMBER(38, 4)
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
 WITH CTE1 AS
 (
  select
   0 AS RESULT
 ),
 CTE2 AS
 (
  select
   SubTotal AS FIRSTVALUE
  from
   Purchasing.PurchaseOrderHeader
  where
   PurchaseOrderID = 1
 ),
 CTE3 AS
 (
  select
   SubTotal AS SECONDVALUE
  from
   Purchasing.PurchaseOrderHeader
  where
   PurchaseOrderID = 2
 ),
 CTE4 AS
 (
  SELECT
   CASE
    WHEN (
     SELECT
      FIRSTVALUE
     FROM
      CTE2
    ) is not null
     THEN (
     select
      (
       SELECT
        RESULT
       FROM
        CTE1
      ) + (
       SELECT
        FIRSTVALUE
       FROM
        CTE2
      ) AS RESULT)
   END AS RESULT
 ),
 CTE5 AS
 (
  SELECT
   CASE
    WHEN (
     SELECT
      SECONDVALUE
     FROM
      CTE3
    ) is not null
     THEN (
     select
      (
       SELECT
        RESULT
       FROM
        CTE1
      ) + (
       SELECT
        SECONDVALUE
       FROM
        CTE3
      ) AS RESULT)
    ELSE (SELECT
     RESULT
    FROM
     CTE4)
   END AS RESULT
 )
 SELECT
  RESULT
 FROM
  CTE5
$$;

SELECT
 PURCHASING.Foo() AS Result;
Copy
Ergebnis

RESULT

473.1415

Zwei oder mehrere RETURN-Anweisungen

Bei diesem Muster wird der IF-Block, der die RETURN-Klausel enthält, die den Codefluss unterbricht, am Ende des Bodys hinzugefügt, wie die letzte auszuführende Anweisung in einem CASE-Ausdruck.

Grundlegender Fall

In diesem speziellen Szenario gibt es keine Logik zwischen der bedingten RETURN-Anweisung und der abschließenden RETURN-Anweisung, so dass der gesamte Text-Bodys einem einzigen CASE EXPRESSION zugeordnet wird.

SQL Server
Abfrage
CREATE OR ALTER FUNCTION [PURCHASING].[FOO] ()
RETURNS INT
AS
BEGIN
 IF exists (SELECT PreferredVendorStatus FROM Purchasing.Vendor v )
  RETURN 1

 RETURN 0
END

GO

SELECT PURCHASING.FOO() as result;
Copy
Ergebnis

result

1

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION PURCHASING.FOO ()
RETURNS INT
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
 SELECT
  CASE
   WHEN exists (SELECT
     PreferredVendorStatus
    FROM
     Purchasing.Vendor v
   )
    THEN 1
   ELSE 0
  END
$$;

SELECT
 PURCHASING.FOO() as result;
Copy
Ergebnis

RESULT

1

Allgemeine Tabellenausdrücke

Allgemeine Tabellenausdrücke bleiben im ursprünglichen Code erhalten und werden mit den generierten verkettet. SnowConvert AI kann zuerst alle ursprünglichen COMMON TABLE EXPRESSION-Namen identifizieren, um die Generierunmg doppelter Namen zu vermeiden.

SQL Server
Abfrage
CREATE OR ALTER FUNCTION [PURCHASING].[FOO] 
(
 @status INT
) 
Returns INT
As
Begin 
 Declare @result as int = 0

 ;WITH ctetable(RevisionNumber) as 
 (
  SELECT RevisionNumber
  FROM Purchasing.PurchaseOrderHeader poh
  where poh.Status = @status
 ),
 finalCte As
 (
  SELECT RevisionNumber FROM ctetable 
 )
 
 Select @result = count(RevisionNumber) from finalCte 
 return @result;
End

GO

SELECT PURCHASING.FOO(4) as result;
Copy
Ergebnis

result

3689

Snowflake
Abfrage
CREATE OR REPLACE FUNCTION PURCHASING.FOO (STATUS INT)
Returns INT
LANGUAGE SQL
COMMENT = '{"origin":"sf_sc","name":"snowconvert","version":{"major":1, "minor":0},"attributes":{"component":"transact"}}'
AS
$$
 WITH CTE1 AS
 (
  SELECT
   0 AS RESULT
 ),
 ctetable (
  RevisionNumber
 ) as
  (
   SELECT
   RevisionNumber
   FROM
   Purchasing.PurchaseOrderHeader poh
   where
   poh.Status = STATUS
  ),
  finalCte As
  (
   SELECT
   RevisionNumber
  FROM
   ctetable
  ),
  CTE2 AS
  (
  Select
   COUNT(RevisionNumber) AS RESULT from
   finalCte
  )
  SELECT
  RESULT
  FROM
  CTE2
$$;

SELECT
  PURCHASING.FOO(4) as result;
Copy
Ergebnis

RESULT

3689

In JavaScript UDFs umwandeln

Wenn es mehrere Anweisungen gibt und die Funktion in keiner Weise auf die Datenbank zugreift, kann sie unter Beibehaltung der Funktionsäquivalenz in eine JavaScript-Funktion umgewandelt werden

SQL Server
Abfrage 1
CREATE OR ALTER FUNCTION PURCHASING.GetFiscalYear 
(
 @DATE AS DATETIME
)
RETURNS INT
AS
BEGIN
 DECLARE @FiscalYear AS INT
 DECLARE @CurMonth AS INT
 SET @CurMonth = DATEPART(M,@DATE)
 SET @FiscalYear = DATEPART(YYYY, @DATE)
 IF (@CurMonth >= 7)
 BEGIN
  SET @FiscalYear = @FiscalYear + 1 
 END
 RETURN @FiscalYear
END

GO

SELECT PURCHASING.GetFiscalYear('2020-10-10') as DATE;
Copy
Abfrage 2
CREATE OR ALTER FUNCTION PURCHASING.[getCleanChargeCode]
(
 @ChargeCode varchar(50)
)
returns varchar(50) as
begin
 declare @CleanChargeCode varchar(50),@Len int,@Pos int=2
 set @Pos=LEN(@ChargeCode)-1
 while @Pos > 1
 begin
  set @CleanChargeCode=RIGHT(@ChargeCode,@Pos)
  if TRY_CAST(@CleanChargeCode as bigint) is not null
   return @CleanChargeCode
  set @Pos=@Pos-1
 end
 set @Pos=LEN(@ChargeCode)-1
 while @Pos > 1
 begin
  set @CleanChargeCode=LEFT(@ChargeCode,@Pos)
  if TRY_CAST(@CleanChargeCode as bigint) is not null
   return @CleanChargeCode
  set @Pos=@Pos-1
 end
 return null
end

GO

SELECT PURCHASING.[getCleanChargeCode]('16test') AS CleanChargeCode;
Copy
Ergebnis 1

DATE

2021

Ergebnis 2

CleanChargeCode

16

Snowflake
Abfrage 1
!!!RESOLVE EWI!!! /*** SSC-EWI-0068 - USER DEFINED FUNCTION WAS TRANSFORMED TO SNOWFLAKE PROCEDURE ***/!!!
CREATE OR REPLACE PROCEDURE PURCHASING.GetFiscalYear (DATE TIMESTAMP_NTZ(3))
RETURNS VARCHAR
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "07/11/2025",  "domain": "no-domain-provided" }}'
EXECUTE AS CALLER
AS
$$
 DECLARE
  FISCALYEAR INT;
  CURMONTH INT;
 BEGIN
   
   
  CURMONTH := DATE_PART(month, :DATE :: TIMESTAMP);
  FISCALYEAR := DATE_PART(year, :DATE :: TIMESTAMP);
  IF ((:CURMONTH >= 7)) THEN
   BEGIN
    FISCALYEAR := :FISCALYEAR + 1;
   END;
  END IF;
  RETURN :FISCALYEAR;
 END;
$$;

SELECT
 PURCHASING.GetFiscalYear('2020-10-10') !!!RESOLVE EWI!!! /*** SSC-EWI-0067 - UDF WAS TRANSFORMED TO SNOWFLAKE PROCEDURE, CALLING PROCEDURES INSIDE QUERIES IS NOT SUPPORTED ***/!!! as DATE;
Copy
Abfrage 2
!!!RESOLVE EWI!!! /*** SSC-EWI-0068 - USER DEFINED FUNCTION WAS TRANSFORMED TO SNOWFLAKE PROCEDURE ***/!!!
CREATE OR REPLACE PROCEDURE PURCHASING.getCleanChargeCode (CHARGECODE STRING)
RETURNS VARCHAR
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "07/16/2025",  "domain": "no-domain-provided" }}'
EXECUTE AS CALLER
AS
$$
 DECLARE
  CLEANCHARGECODE VARCHAR(50);
  LEN INT;
  POS INT := 2;
 BEGIN
   
  POS := LEN(:CHARGECODE)-1;
  WHILE (:POS > 1) LOOP
   CLEANCHARGECODE := RIGHT(:CHARGECODE, :POS);
   IF (CAST(:CLEANCHARGECODE AS BIGINT) /*** SSC-FDM-TS0005 - TRY_CONVERT/TRY_CAST COULD NOT BE CONVERTED TO TRY_CAST ***/!!!RESOLVE EWI!!! /*** SSC-EWI-TS0074 - CAST RESULT MAY BE DIFFERENT FROM TRY_CAST FUNCTION DUE TO MISSING DEPENDENCIES ***/!!! is not null) THEN
    RETURN :CLEANCHARGECODE;
   END IF;
   POS := :POS -1;
  END LOOP;
  POS := LEN(:CHARGECODE)-1;
  WHILE (:POS > 1) LOOP
   CLEANCHARGECODE := LEFT(:CHARGECODE, :POS);
   IF (CAST(:CLEANCHARGECODE AS BIGINT) /*** SSC-FDM-TS0005 - TRY_CONVERT/TRY_CAST COULD NOT BE CONVERTED TO TRY_CAST ***/!!!RESOLVE EWI!!! /*** SSC-EWI-TS0074 - CAST RESULT MAY BE DIFFERENT FROM TRY_CAST FUNCTION DUE TO MISSING DEPENDENCIES ***/!!! is not null) THEN
    RETURN :CLEANCHARGECODE;
   END IF;
   POS := :POS -1;
  END LOOP;
  RETURN null;
 END;
$$;

SELECT
 PURCHASING.getCleanChargeCode('16test') !!!RESOLVE EWI!!! /*** SSC-EWI-0067 - UDF WAS TRANSFORMED TO SNOWFLAKE PROCEDURE, CALLING PROCEDURES INSIDE QUERIES IS NOT SUPPORTED ***/!!! AS CleanChargeCode;
Copy
Ergebnis 1

DATE

2021.0

Ergebnis 2

CLEANCHARGECODE

16

Bekannte Probleme

Warnung

Benutzerdefinierte Funktionen können nicht verwendet werden, um Aktionen durchzuführen, die den Zustand der Datenbank verändern

Warnung

Benutzerdefinierte Funktionen können keine OUTPUT INTO- Klausel enthalten, die eine Tabelle als Ziel hat

Warnung

Benutzerdefinierte Funktionen können DECLARE, OPEN, FETCH, CLOSE oder DEALLOCATE für einen CURSOR nicht verwenden. Verwenden Sie eine gespeicherte Prozedur, wenn Sie Cursors verwenden müssen.

Warnung

Benutzerdefinierte Funktionen können keine CONTROL-OF-FLOW-Anweisungen wie WHILE ausführen, wenn es mindestens einen Aufruf an die Datenbank gibt

Warnung

Benutzerdefinierte Funktionen mit Referenzen auf andere benutzerdefinierte Funktionen, die in gespeicherte Prozeduren umgewandelt wurden, werden ebenfalls in Prozeduren umgewandelt.

Warnung

Benutzerdefinierte Funktionen, die @@ROWCOUNT verwenden, werden in SQL nicht unterstützt und sollten in gespeicherte Prozeduren umgewandelt werden, um die Funktionsäquivalenz zu wahren.

Warnung

Benutzerdefinierte Funktionen mit SELECT Anweisungen, die sich selbst eine Variable zuweisen, werden in Snowflake nicht unterstützt. Siehe auch SELECT @local_variable

Für alle nicht unterstützten Fälle prüfen Sie bitte die entsprechenden EWIs und die unten stehenden Muster, um Empfehlungen und mögliche Umgehungslösungen zu erhalten.

Andere Bedingungen als IF/ELSE-Anweisungen neben Abfragen

Das nächste Szenario beinhaltet die Verwendung der „WHILE-Anweisung“ zusammen mit anderen Abfragen. Das Problem bei diesem Beispiel ist, dass es keine Möglichkeit gibt, die WHILE-Anweisung innerhalb der WITH-Klausel des Haupt-Select in eine CTE umzuwandeln. Dadurch sind wir gezwungen, diese Anweisung in eine JavaScript-Prozedur umzuwandeln, um die gleiche Logik zu erhalten.

SQL Server
Abfrage
CREATE OR ALTER FUNCTION PURCHASING.FOO()
RETURNS INT
AS
BEGIN
    DECLARE @i int = 0, @p int;
    Select @p = COUNT(*) FROM PURCHASING.VENDOR
    
    WHILE (@p < 1000)
    BEGIN
        SET @i = @i + 1
        SET @p = @p + @i
    END
        
    IF (@i = 6)
        RETURN 1
    
    RETURN @p
END

GO

SELECT PURCHASING.FOO() as result;
Copy
Ergebnis

result

1007

Snowflake

Abfrage
 !!!RESOLVE EWI!!! /*** SSC-EWI-0068 - USER DEFINED FUNCTION WAS TRANSFORMED TO SNOWFLAKE PROCEDURE ***/!!!
CREATE OR REPLACE PROCEDURE PURCHASING.FOO ()
RETURNS VARCHAR
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "07/11/2025",  "domain": "no-domain-provided" }}'
EXECUTE AS CALLER
AS
$$
    DECLARE
        I INT := 0;
        P INT;
    BEGIN
         
        Select
            COUNT(*)
        INTO
            :P
 FROM
            PURCHASING.VENDOR;
        WHILE (:P < 1000) LOOP
            I := :I + 1;
            P := :P + :I;
        END LOOP;
        IF ((:I = 6)) THEN
            RETURN 1;
        END IF;
        RETURN :P;
    END;
$$;

SELECT
    PURCHASING.FOO() !!!RESOLVE EWI!!! /*** SSC-EWI-0067 - UDF WAS TRANSFORMED TO SNOWFLAKE PROCEDURE, CALLING PROCEDURES INSIDE QUERIES IS NOT SUPPORTED ***/!!! as result;
Copy
Ergebnis

FOO

1007

Zuweisung einer Variablen unter Verwendung ihres eigenen Werts bei der Iteration durch einen Rowset

Im folgenden Beispiel wird die Variable @names verwendet, um mehrere Werte aus einer Spalte zu einer einzigen Zeichenfolge zu verketten. Die Variable wird wie gezeigt bei jeder Iteration aktualisiert, was von SnowFlake UDFs nicht unterstützt wird. Für dieses Szenario sollte die Funktion in eine Prozedur umgewandelt werden.

SQL Server

Abfrage
CREATE OR ALTER FUNCTION PURCHASING.FOO()
RETURNS VARCHAR(8000)
AS
BEGIN
    DECLARE @names varchar(8000)
    SET @names = ''
    SELECT @names = ISNULL(@names + ' ', '') + Name from Purchasing.Vendor v 
    return @names              
END

GO

select PURCHASING.FOO() as names;
Copy
Ergebnis

names

Australia Bike Retailer Allenson Cycles Advanced Bicycles Trikes, Inc. Morgan Bike Accessories Cycling Master Chicago Rent-All Greenwood Athletic Company Compete Enterprises, Inc International Light Speed Training Systems Gardner Touring Cycles Internati

Snowflake-Abfrage

!!!RESOLVE EWI!!! /*** SSC-EWI-0068 - USER DEFINED FUNCTION WAS TRANSFORMED TO SNOWFLAKE PROCEDURE ***/!!!
CREATE OR REPLACE PROCEDURE PURCHASING.FOO ()
RETURNS VARCHAR
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "07/11/2025",  "domain": "no-domain-provided" }}'
EXECUTE AS CALLER
AS
$$
    DECLARE
        NAMES VARCHAR(8000);
    BEGIN
         
        NAMES := '';
        SELECT
            NVL(:NAMES || ' ', '') + Name
        INTO
            :NAMES
        from
            Purchasing.Vendor v;
        RETURN :NAMES;
    END;
$$;

select
    PURCHASING.FOO() !!!RESOLVE EWI!!! /*** SSC-EWI-0067 - UDF WAS TRANSFORMED TO SNOWFLAKE PROCEDURE, CALLING PROCEDURES INSIDE QUERIES IS NOT SUPPORTED ***/!!! as names;
Copy

Warnung

Beachten Sie bei den oben beschriebenen Szenarien die folgenden Beschränkungen:

  1. Alle Aufrufe von benutzerdefinierten Funktionen in DML-Abfragen wie SELECT, INSERT, DELETE, UPDATE oder MERGE werden fehlschlagen, da Aufrufe von gespeicherten Prozeduren in diesen Abfragen nicht erlaubt sind.

  2. Aufrufen von benutzerdefinierten Funktionen innerhalb von Prozeduren sollte das Schlüsselwort CALL vorangestellt werden.

  3. Benutzerdefinierte Funktionen, die in COMPUTED COLUMNS verwendet werden, schlagen bei der Ausführung fehl.

Zugehörige EWIs

  1. [SSC-EWI-0067](../../general/technical-documentation/issues-and-troubleshooting/conversion-issues/generalEWI. md#ssc-ewi-0067): UDF wurde in eine Snowflake-Prozedur umgewandelt, der Aufruf von Prozeduren innerhalb einer Abfrage wird nicht unterstützt.

  2. SSC-EWI-0068: Die benutzerdefinierte Funktion wurde in eine Snowflake-Prozedur umgewandelt.

  3. [SSC-EWI-0073](../../general/technical-documentation/issues-and-troubleshooting/conversion-issues/generalEWI. md#ssc-ewi-0073): Überprüfung der Funktionsäquivalenz ausstehend.

UDF für Snowflake-Skript (SCALAR)

Übersetzungsreferenz für benutzerdefinierte SQL Server-Skalarfunktionen für Snowflake Scripting UDFs

Applies to
  • SQL Server

  • Azure Synapse Analytics

Beschreibung

SnowConvert unterstützt die Übersetzung von benutzerdefinierten SQL Server-Sklalarfunktionen direkt in Snowflake Scripting UDFs (SnowScript UDFs), wenn sie bestimmte Kriterien erfüllen, anstatt alle Funktionen in gespeicherte Prozeduren zu konvertieren.

Snowflake Scripting UDFs sind benutzerdefinierte Funktionen, die mit Snowflakes prozeduraler Sprachsyntax (SnowScript) innerhalb eines SQL UDF-Textkörpers geschrieben wurden. Sie unterstützen Variablen, Schleifen, bedingte Logik und die Ausnahmebehandlung.

Wenn Funktionen zu SnowScript UDFs werden

SnowConvert analysiert jeden SQL Server-Funktion und ermittelt automatisch das entsprechende Snowflake-Ziel. Eine Funktion wird zu einer SnowScript UDF, wenn sie nur prozedurale Logik ohne Datenzugriffsoperationen enthält.

Beispielhafte Quellcode-Muster

Einfache Berechnungsfunktion

Eine einfache Skalarfunktion, die Berechnungen durchführt, ohne Daten abzufragen.

SQL Server
CREATE FUNCTION dbo.CalculateProfit
(
    @Cost DECIMAL(10,2),
    @Revenue DECIMAL(10,2)
)
RETURNS DECIMAL(10,2)
AS
BEGIN
    DECLARE @Profit DECIMAL(10,2)
    SET @Profit = @Revenue - @Cost
    RETURN @Profit
END
GO

SELECT dbo.CalculateProfit(100.00, 150.00) as Profit;
Copy
Ergebnis

Profit

50,00

Snowflake (SnowScript UDF)
CREATE OR REPLACE FUNCTION dbo.CalculateProfit (COST DECIMAL(10,2), REVENUE DECIMAL(10,2))
RETURNS DECIMAL(10, 2)
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "10/09/2025",  "domain": "no-domain-provided",  "migrationid": "QsqZARsvG3aeleeXZB43fg==" }}'
AS
$$
   DECLARE
 PROFIT DECIMAL(10, 2);
   BEGIN
  
 PROFIT := :REVENUE - :COST;
 RETURN :PROFIT;
   END;
$$;

SELECT
   dbo.CalculateProfit(100.00, 150.00) as Profit;
Copy
Ergebnis

PROFIT

50,00

Funktion mit bedingter Logik (IF/ELSE)

Funktionen mit IF/ELSE-Anweisungen für Geschäftslogik.

SQL Server
CREATE FUNCTION dbo.GetDiscountRate
(
    @CustomerType VARCHAR(20),
    @OrderAmount DECIMAL(10,2)
)
RETURNS DECIMAL(5,2)
AS
BEGIN
    DECLARE @Discount DECIMAL(5,2)
    
    IF @CustomerType = 'Premium'
        SET @Discount = 0.15
    ELSE IF @CustomerType = 'Standard'
        SET @Discount = 0.10
    ELSE
        SET @Discount = 0.05
    
    IF @OrderAmount > 1000
        SET @Discount = @Discount + 0.05
    
    RETURN @Discount
END
GO

SELECT dbo.GetDiscountRate('Premium', 1200.00) as DiscountRate;
Copy
Ergebnis

DiscountRate

0.20

Snowflake (SnowScript UDF)
CREATE OR REPLACE FUNCTION dbo.GetDiscountRate (CUSTOMERTYPE STRING, ORDERAMOUNT DECIMAL(10,2))
RETURNS DECIMAL(5, 2)
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "10/09/2025",  "domain": "no-domain-provided",  "migrationid": "QsqZARsvG3aeleeXZB43fg==" }}'
AS
$$
   DECLARE
 DISCOUNT DECIMAL(5, 2);
   BEGIN
  
 IF (:CUSTOMERTYPE = 'Premium') THEN
 DISCOUNT := 0.15;
 ELSEIF (:CUSTOMERTYPE = 'Standard') THEN
 DISCOUNT := 0.10;
 ELSE
 DISCOUNT := 0.05;
 END IF;
 IF (:ORDERAMOUNT > 1000) THEN
 DISCOUNT := :DISCOUNT + 0.05;
 END IF;
 RETURN :DISCOUNT;
   END;
$$;

SELECT
   dbo.GetDiscountRate('Premium', 1200.00) as DiscountRate;
Copy
Ergebnis

DISCOUNTRATE

0.20

Funktion mit WHILE-Schleife

Funktionen mit WHILE-Schleifen für iterative Berechnungen.

SQL Server
CREATE FUNCTION dbo.Factorial
(
    @Number INT
)
RETURNS BIGINT
AS
BEGIN
    DECLARE @Result BIGINT = 1
    DECLARE @Counter INT = 1
    
    WHILE @Counter <= @Number
    BEGIN
        SET @Result = @Result * @Counter
        SET @Counter = @Counter + 1
    END
    
    RETURN @Result
END
GO

SELECT dbo.Factorial(5) as FactorialResult;
Copy
Ergebnis

FactorialResult

120

Snowflake (SnowScript UDF)
CREATE OR REPLACE FUNCTION dbo.Factorial (NUMBER INT)
RETURNS BIGINT
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "10/09/2025",  "domain": "no-domain-provided",  "migrationid": "QsqZARsvG3aeleeXZB43fg==" }}'
AS
$$
  DECLARE
  RESULT BIGINT := 1;
  COUNTER INT := 1;
  BEGIN
  
    WHILE (:COUNTER <= :NUMBER) LOOP
      RESULT := :RESULT * :COUNTER;
      COUNTER := :COUNTER + 1;
    END LOOP;
    RETURN :RESULT;
  END;
$$;

SELECT
   dbo.Factorial(5) as FactorialResult;
Copy
Ergebnis

FACTORIALRESULT

120

Zeichenfolgenbearbeitungsfunktion

Komplexe Zeichenfolgenoperationen mit Schleifen und bedingter Logik.

SQL Server
CREATE FUNCTION dbo.CleanPhoneNumber
(
    @Phone VARCHAR(20)
)
RETURNS VARCHAR(10)
AS
BEGIN
    DECLARE @Clean VARCHAR(10) = ''
    DECLARE @i INT = 1
    DECLARE @Char CHAR(1)
    
    WHILE @i <= LEN(@Phone)
    BEGIN
        SET @Char = SUBSTRING(@Phone, @i, 1)
        IF @Char BETWEEN '0' AND '9'
            SET @Clean = @Clean + @Char
        SET @i = @i + 1
    END
    
    RETURN @Clean
END
GO

SELECT dbo.CleanPhoneNumber('(555) 123-4567') as CleanPhone;
Copy
Ergebnis

CleanPhone

5551234567

Snowflake (SnowScript UDF)
CREATE OR REPLACE FUNCTION dbo.CleanPhoneNumber (PHONE STRING)
RETURNS VARCHAR(10)
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "10/09/2025",  "domain": "no-domain-provided",  "migrationid": "QsqZARsvG3aeleeXZB43fg==" }}'
AS
$$
   DECLARE
 CLEAN VARCHAR(10) := '';
 I INT := 1;
 CHAR CHAR(1);
   BEGIN
  
  
  
 WHILE (:I <= LEN(:PHONE)) LOOP
 CHAR := SUBSTRING(:PHONE, :I, 1);
 IF (:CHAR BETWEEN '0' AND '9') THEN
  CLEAN := :CLEAN + :CHAR;
 END IF;
 I := :I + 1;
 END LOOP;
 RETURN :CLEAN;
   END;
$$;

SELECT
   dbo.CleanPhoneNumber('(555) 123-4567') as CleanPhone;
Copy
Ergebnis

CLEANPHONE

5551234567

CASE-Anweisungslogik

Funktionen mit CASE-Ausdrücke zur Kategorisierung.

SQL Server
CREATE FUNCTION dbo.GetGrade
(
    @Score INT
)
RETURNS CHAR(1)
AS
BEGIN
    DECLARE @Grade CHAR(1)
    
    SET @Grade = CASE
        WHEN @Score >= 90 THEN 'A'
        WHEN @Score >= 80 THEN 'B'
        WHEN @Score >= 70 THEN 'C'
        WHEN @Score >= 60 THEN 'D'
        ELSE 'F'
    END
    
    RETURN @Grade
END
GO

SELECT dbo.GetGrade(85) as Grade;
Copy
Ergebnis

Grade

B

Snowflake (SnowScript UDF)
CREATE OR REPLACE FUNCTION dbo.GetGrade (SCORE INT)
RETURNS CHAR(1)
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "10/09/2025",  "domain": "no-domain-provided",  "migrationid": "QsqZARsvG3aeleeXZB43fg==" }}'
AS
$$
   DECLARE
 GRADE CHAR(1);
   BEGIN
  
 CASE
 WHEN :SCORE >= 90 THEN
  GRADE := 'A';
 WHEN :SCORE >= 80 THEN
  GRADE := 'B';
 WHEN :SCORE >= 70 THEN
  GRADE := 'C';
 WHEN :SCORE >= 60 THEN
  GRADE := 'D';
 ELSE
  GRADE := 'F';
 END;
 RETURN :GRADE;
   END;
$$;

SELECT
   dbo.GetGrade(85) as Grade;
Copy
Ergebnis

GRADE

B

Select Into variable assingment

Functions using simple select into for variable assignment.

SQL Server
CREATE FUNCTION dbo.CalculatePrice
(
    @BasePrice DECIMAL(10, 2),
    @Quantity INT
)
RETURNS DECIMAL(10, 2)
AS
BEGIN
    DECLARE @Discount DECIMAL(5, 2);
    DECLARE @Subtotal DECIMAL(10, 2);
    DECLARE @FinalPrice DECIMAL(10, 2);
    
    SELECT @Discount = CASE 
                           WHEN @Quantity >= 10 THEN 0.15
                           WHEN @Quantity >= 5 THEN 0.10
                           ELSE 0.05
                       END,
           @Subtotal = @BasePrice * @Quantity;
    
    SET @FinalPrice = @Subtotal * (1 - @Discount);
    
    RETURN @FinalPrice;
END;
Copy
Ergebnis

CALCULATEPRICE(100, 3)

285

Snowflake (SnowScript UDF)
CREATE OR REPLACE FUNCTION dbo.CalculatePrice (BASEPRICE DECIMAL(10, 2), QUANTITY INT)
RETURNS DECIMAL(10, 2)
LANGUAGE SQL
COMMENT = '{ "origin": "sf_sc", "name": "snowconvert", "version": {  "major": 0,  "minor": 0,  "patch": "0" }, "attributes": {  "component": "transact",  "convertedOn": "11/26/2025",  "domain": "no-domain-provided",  "migrationid": "T8GaASfFsHeOffK4v3SnIQ==" }}'
AS
$$
    DECLARE
        DISCOUNT DECIMAL(5, 2);
        SUBTOTAL DECIMAL(10, 2);
        FINALPRICE DECIMAL(10, 2);
    BEGIN
         
         
         
        DISCOUNT := CASE
                                      WHEN :QUANTITY >= 10 THEN 0.15
                                      WHEN :QUANTITY >= 5 THEN 0.10
                                      ELSE 0.05
                                  END;
        SUBTOTAL := :BASEPRICE * :QUANTITY;
        FINALPRICE := :SUBTOTAL * (1 - :DISCOUNT);
        RETURN :FINALPRICE;
    END;
$$;
Copy
Ergebnis

CALCULATEPRICE(100, 3)

285

Bekannte Probleme

Warnung

SnowConvert AI will not translate UDFs containing the following elements into SnowScripting UDFs, as these features are unsupported in SnowScripting UDFs:

  • Auf Datenbanktabellen zugreifen

  • Cursor verwenden

  • Andere UDFs aufrufen

  • Aggregat- oder Fensterfunktionen enthalten

  • DML-Operationen (INSERT/UPDATE/DELETE) ausführen

  • Resultsets zurückgeben

Zugehörige EWIs

  1. [SSC-EWI-0067](../../general/technical-documentation/issues-and-troubleshooting/conversion-issues/generalEWI. md#ssc-ewi-0067): UDF wurde in eine Snowflake-Prozedur umgewandelt, der Aufruf von Prozeduren innerhalb einer Abfrage wird nicht unterstützt.

  2. SSC-EWI-0068: Die benutzerdefinierte Funktion wurde in eine Snowflake-Prozedur umgewandelt.

  3. [SSC-EWI-0073](../../general/technical-documentation/issues-and-troubleshooting/conversion-issues/generalEWI. md#ssc-ewi-0073): Überprüfung der Funktionsäquivalenz ausstehend.