CREATE EMBEDDED FUNCTION
Introduced or updated: v1.2.339
Creates an Embedded UDF using programming languages (Python, JavaScript, WASM). Uses the same unified $$ syntax as SQL functions for consistency.
Syntax
CREATE [ OR REPLACE ] FUNCTION [ IF NOT EXISTS ] <function_name>
( [<parameter_list>] )
RETURNS <return_type>
LANGUAGE <language>
[IMPORTS = ('<import_path>', ...)]
[PACKAGES = ('<package_path>', ...)]
HANDLER = '<handler_name>'
AS $$ <function_code> $$
[ DESC='<description>' ]
Where:
<parameter_list>: Comma-separated list of parameters with their types (e.g.,x INT, name VARCHAR)<return_type>: The data type of the function's return value<language>: Programming language (python,javascript,wasm)<import_path>: Stage files to import (e.g.,@s_udf/your_file.zip)<package_path>: Packages to install from pypi (Python only)<handler_name>: Name of the function in the code to call<function_code>: The implementation code in the specified language
Supported Languages
| Language | Description | Enterprise Required | Package Support |
|---|---|---|---|
python | Python 3 with standard library | Yes | PyPI packages via PACKAGES |
javascript | Modern JavaScript (ES6+) | No | No |
wasm | WebAssembly (Rust compiled) | No | No |
Data Type Mappings
Python
| Databend Type | Python Type |
|---|---|
| NULL | None |
| BOOLEAN | bool |
| INT | int |
| FLOAT/DOUBLE | float |
| DECIMAL | decimal.Decimal |
| VARCHAR | str |
| BINARY | bytes |
| LIST | list |
| MAP | dict |
| STRUCT | object |
| JSON | dict/list |
JavaScript
| Databend Type | JavaScript Type |
|---|---|
| NULL | null |
| BOOLEAN | Boolean |
| INT | Number |
| FLOAT/DOUBLE | Number |
| DECIMAL | BigDecimal |
| VARCHAR | String |
| BINARY | Uint8Array |
| DATE/TIMESTAMP | Date |
| ARRAY | Array |
| MAP | Object |
| STRUCT | Object |
| JSON | Object/Array |
Access Control Requirements
| Privilege | Object Type | Description |
|---|---|---|
| SUPER | Global, Table | Operates a UDF |
To create an embedded function, the user performing the operation or the current_role must have the SUPER privilege.
Examples
Python Function
-- Simple Python function
CREATE FUNCTION calculate_age_py(VARCHAR)
RETURNS INT
LANGUAGE python HANDLER = 'calculate_age'
AS $$
from datetime import datetime
def calculate_age(birth_date_str):
birth_date = datetime.strptime(birth_date_str, '%Y-%m-%d')
today = datetime.now()
age = today.year - birth_date.year
if (today.month, today.day) < (birth_date.month, birth_date.day):
age -= 1
return age
$$;
-- Use the function
SELECT calculate_age_py('1990-05-15') AS age;
JavaScript Function
-- JavaScript function for age calculation
CREATE FUNCTION calculate_age_js(VARCHAR)
RETURNS INT
LANGUAGE javascript HANDLER = 'calculateAge'
AS $$
export function calculateAge(birthDateStr) {
const birthDate = new Date(birthDateStr);
const today = new Date();
let age = today.getFullYear() - birthDate.getFullYear();
const monthDiff = today.getMonth() - birthDate.getMonth();
if (monthDiff < 0 || (monthDiff === 0 && today.getDate() < birthDate.getDate())) {
age--;
}
return age;
}
$$;
-- Use the function
SELECT calculate_age_js('1990-05-15') AS age;
Python Function with Packages
CREATE FUNCTION ml_model_score()
RETURNS FLOAT
LANGUAGE python IMPORTS = ('@s1/model.zip') PACKAGES = ('scikit-learn') HANDLER = 'model_score'
AS $$
from sklearn.datasets import load_iris
from sklearn.model_selection import train_test_split
from sklearn.ensemble import RandomForestClassifier
def model_score():
X, y = load_iris(return_X_y=True)
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.25, random_state=42)
model = RandomForestClassifier()
model.fit(X_train, y_train)
return model.score(X_test, y_test)
$$;
-- Use the function
SELECT ml_model_score() AS accuracy;
WASM Function
First, create a Rust project and compile to WASM:
# Cargo.toml
[package]
name = "arrow-udf-example"
version = "0.1.0"
[lib]
crate-type = ["cdylib"]
[dependencies]
arrow-udf = "0.8"
// src/lib.rs
use arrow_udf::function;
#[function("fib(int) -> int")]
fn fib(n: i32) -> i32 {
let (mut a, mut b) = (0, 1);
for _ in 0..n {
let c = a + b;
a = b;
b = c;
}
a
}
Build and deploy:
cargo build --release --target wasm32-wasip1
# Upload to stage
CREATE STAGE s_udf;
PUT fs:///target/wasm32-wasip1/release/arrow_udf_example.wasm @s_udf/;
-- Create WASM function
CREATE FUNCTION fib_wasm(INT)
RETURNS INT
LANGUAGE wasm HANDLER = 'fib'
AS $$@s_udf/arrow_udf_example.wasm$$;
-- Use the function
SELECT fib_wasm(10) AS fibonacci_result;