Funkcje zdefiniowane przez użytkownika (UDF) w wykazie aparatu Unity

Ważne

Ta funkcja jest dostępna w publicznej wersji zapoznawczej.

Funkcje zdefiniowane przez użytkownika (UDF) w wykazie aparatu Unity rozszerzają możliwości języka SQL i Python w usłudze Azure Databricks. Umożliwiają one definiowanie, używanie i bezpieczne udostępnianie funkcji niestandardowych w środowiskach obliczeniowych.

Funkcje zdefiniowane przez użytkownika języka Python zarejestrowane jako funkcje w wykazie aparatu Unity różnią się zakresem i obsługą funkcji zdefiniowanych przez użytkownika PySpark w zakresie notesu lub platformy SparkSession. Zobacz Funkcje skalarne zdefiniowane przez użytkownika — Python.

Aby uzyskać pełną dokumentację języka SQL, zobacz CREATE FUNCTION (SQL i Python).

Wymagania

Aby można było używać funkcji zdefiniowanych przez użytkownika w wykazie aparatu Unity, należy spełnić następujące wymagania:

  • Aby użyć kodu języka Python w funkcjach zdefiniowanych przez użytkownika zarejestrowanych w katalogu aparatu Unity, należy użyć bezserwerowego lub pro SQL Warehouse albo klastra z uruchomionym środowiskiem Databricks Runtime 13.3 LTS lub nowszym.
  • Jeśli widok zawiera funkcję UC Python UDF, zakończy się niepowodzeniem w usłudze SQL Classic Warehouses.

Tworzenie funkcji zdefiniowanych przez użytkownika w wykazie aparatu Unity

Aby utworzyć funkcję UDF w wykazie aparatu Unity, użytkownicy muszą mieć uprawnienia USAGE i CREATE dla schematu i użycia w wykazie. Aby uzyskać więcej informacji, zobacz Wykaz aparatu Unity.

Aby uruchomić funkcję zdefiniowaną przez użytkownika, użytkownicy muszą mieć uprawnienia EXECUTE w funkcji zdefiniowanej przez użytkownika. Użytkownicy potrzebują również uprawnień USAGE w schemacie i wykazie.

Poniższy przykład rejestruje nową funkcję w schemacie my_schema wykazu aparatu Unity:

CREATE OR REPLACE FUNCTION my_catalog.my_schema.calculate_bmi(weight DOUBLE, height DOUBLE)
RETURNS DOUBLE
LANGUAGE SQL
AS
SELECT weight / (height * height);

Funkcje zdefiniowane przez użytkownika języka Python dla wykazu aparatu Unity używają instrukcji przesunięcia przez znaki podwójnego dolara ($$). Należy również określić mapowanie typu danych. Poniższy przykład rejestruje funkcję zdefiniowaną przez użytkownika, która oblicza indeks masy ciała:

CREATE FUNCTION my_catalog.my_schema.calculate_bmi(weight_kg DOUBLE, height_m DOUBLE)
RETURNS DOUBLE
LANGUAGE PYTHON
AS $$
return weight_kg / (height_m ** 2)
$$;

Teraz możesz użyć tej funkcji wykazu aparatu Unity w zapytaniach SQL lub kodzie PySpark:

SELECT person_id, my_catalog.my_schema.calculate_bmi(weight_kg, height_m) AS bmi
FROM person_data;

Korzystanie z funkcji zdefiniowanej przez użytkownika wykazu aparatu Unity w narzędziu PySpark

from pyspark.sql.functions import expr

result = df.withColumn("bmi", expr("my_catalog.my_schema.calculate_bmi(weight_kg, height_m)"))
display(result)

Uaktualnianie funkcji zdefiniowanej przez użytkownika w zakresie sesji

Uwaga

Składnia i semantyka funkcji zdefiniowanych przez użytkownika języka Python w katalogu aparatu Unity różnią się od zdefiniowanych przez użytkownika języka Python zarejestrowanych na platformie SparkSession. Zobacz funkcje skalarne zdefiniowane przez użytkownika — Python.

Biorąc pod uwagę następującą funkcję zdefiniowaną przez użytkownika opartą na sesji w notesie usługi Azure Databricks:

from pyspark.sql.functions import udf
from pyspark.sql.types import StringType

@udf(StringType())
def greet(name):
    return f"Hello, {name}!"

# Using the session-based UDF
result = df.withColumn("greeting", greet("name"))
result.show()

Aby zarejestrować tę funkcję jako funkcję wykazu aparatu Unity, użyj instrukcji SQL CREATE FUNCTION , jak w poniższym przykładzie:

CREATE OR REPLACE FUNCTION my_catalog.my_schema.greet(name STRING)
RETURNS STRING
LANGUAGE PYTHON
AS $$
return f"Hello, {name}!"
$$

Udostępnianie funkcji zdefiniowanych przez użytkownika w wykazie aparatu Unity

Uprawnienia funkcji zdefiniowanych przez użytkownika są zarządzane na podstawie kontroli dostępu stosowanych do katalogu, schematu lub bazy danych, w której zarejestrowano funkcję zdefiniowanej przez użytkownika. Aby uzyskać więcej informacji, zobacz Wykaz aparatu Unity.

Użyj usługi Azure Databricks SQL lub interfejsu użytkownika obszaru roboczego usługi Azure Databricks, aby udzielić uprawnień użytkownikowi lub grupie (zalecane).

Uprawnienia w interfejsie użytkownika obszaru roboczego

  1. Znajdź katalog i schemat, w którym są przechowywane funkcje zdefiniowane przez użytkownika, i wybierz funkcję zdefiniowanej przez użytkownika.
  2. Poszukaj opcji Uprawnienia w ustawieniach funkcji zdefiniowanej przez użytkownika. Dodaj użytkowników lub grupy i określ typ dostępu, który powinien mieć, na przykład EXECUTE lub MANAGE.

! [Uprawnienia w interfejsie użytkownika obszaru roboczego](.. /_static/images/udf/high res udf permission.gif)

Uprawnienia przy użyciu usługi Azure Databricks SQL

Poniższy przykład przyznaje użytkownikowi uprawnienie EXECUTE dla funkcji:

GRANT EXECUTE ON FUNCTION my_catalog.my_schema.calculate_bmi TO user@example.com;

Aby usunąć uprawnienia, użyj REVOKE polecenia , jak w poniższym przykładzie:

REVOKE EXECUTE ON FUNCTION my_catalog.my_schema.calculate_bmi FROM user@example.com;

Najlepsze rozwiązania dotyczące funkcji zdefiniowanych przez użytkownika

W przypadku funkcji zdefiniowanych przez użytkownika, które muszą być dostępne dla wszystkich użytkowników, usługa Databricks zaleca utworzenie dedykowanego wykazu i schematu z odpowiednimi mechanizmami kontroli dostępu.

W przypadku funkcji zdefiniowanych przez zespół należy użyć dedykowanego schematu w katalogu zespołu na potrzeby magazynowania i zarządzania.

Usługa Azure Databricks zaleca uwzględnienie następujących informacji w dokumentach usługi UDF:

  • Bieżący numer wersji
  • Dziennik zmian do śledzenia modyfikacji w różnych wersjach
  • Cel, parametry i wartość zwracana przez funkcję UDF
  • Przykład użycia funkcji zdefiniowanej przez użytkownika

Oto przykład następujących najlepszych rozwiązań dotyczących funkcji zdefiniowanej przez użytkownika:

CREATE OR REPLACE FUNCTION my_catalog.my_schema.calculate_bmi(weight_kg DOUBLE, height_m DOUBLE)
RETURNS DOUBLE
COMMENT ”Calculates Body Mass Index (BMI) from weight and height.”
LANGUAGE PYTHON
AS $$
 """
Parameters:
calculate_bmi (version 1.2):
- weight_kg (float): Weight of the individual in kilograms.
- height_m (float): Height of the individual in meters.

Returns:
- float: The calculated BMI.

Example Usage:

SELECT calculate_bmi(weight, height) AS bmi FROM person_data;

Change Log:
- 1.0: Initial version.
- 1.1: Improved error handling for zero or negative height values.
- 1.2: Optimized calculation for performance.

 Note: BMI is calculated as weight in kilograms divided by the square of height in meters.
 """
if height_m <= 0:
 return None  # Avoid division by zero and ensure height is positive
return weight_kg / (height_m ** 2)
$$;

Funkcje zdefiniowane przez użytkownika na potrzeby uzyskiwania dostępu do zewnętrznych interfejsów API

Za pomocą funkcji zdefiniowanych przez użytkownika można uzyskiwać dostęp do zewnętrznych interfejsów API z poziomu języka SQL. W poniższym przykładzie użyto biblioteki języka Python requests do utworzenia żądania HTTP.

Uwaga

Funkcje zdefiniowane przez użytkownika języka Python umożliwiają ruch sieciowy TCP/UDP przez porty 80, 443 i 53 przy użyciu bezserwerowych obliczeń lub obliczeń skonfigurowanych w trybie dostępu współdzielonego.

CREATE FUNCTION my_catalog.my_schema.get_food_calories(food_name STRING)
RETURNS DOUBLE
LANGUAGE PYTHON
AS $$
import requests

api_url = f"https://example-food-api.com/nutrition?food={food_name}"
response = requests.get(api_url)

if response.status_code == 200:
   data = response.json()
   # Assuming the API returns a JSON object with a 'calories' field
   calories = data.get('calories', 0)
   return calories
else:
   return None  # API request failed

$$;

Funkcje zdefiniowane przez użytkownika na potrzeby zabezpieczeń i zgodności

Użyj funkcji zdefiniowanych przez użytkownika języka Python, aby zaimplementować niestandardowe tokeny, maskowanie danych, redaction lub mechanizmy szyfrowania.

Poniższy przykład maskuje tożsamość adresu e-mail przy zachowaniu długości i domeny:

CREATE OR REPLACE FUNCTION my_catalog.my_schema.mask_email(email STRING)
RETURNS STRING
LANGUAGE PYTHON
AS $$
parts = email.split('@')
masked_username = username[0] + '*' * (len(username) - 2) + username[-1]
return f"{masked_username}@{domain}"
$$

Poniższy przykład dotyczy tej funkcji zdefiniowanej przez użytkownika w definicji widoku dynamicznego:

-- First, create the view
CREATE OR REPLACE VIEW my_catalog.my_schema.masked_customer_view AS
SELECT
  id,
  name,
  my_catalog.my_schema.mask_email(email) AS email
FROM my_catalog.my_schema.customer_data;

-- Now you can query the view
SELECT * FROM my_catalog.my_schema.masked_customer_view;
+---+------------+------------------------+------------------------+
| id|        name|                   email|           masked_email |
+---+------------+------------------------+------------------------+
|  1|    John Doe|   john.doe@example.com |  j*******e@example.com |
|  2| Alice Smith|alice.smith@company.com |a**********h@company.com|
|  3|   Bob Jones|    bob.jones@email.org |   b********s@email.org |
+---+------------+------------------------+------------------------+

Ograniczenia

  • Można zdefiniować dowolną liczbę funkcji języka Python w funkcji UDF języka Python, ale wszystkie muszą zwracać wartość skalarną.
  • Funkcje języka Python muszą obsługiwać wartości NULL niezależnie, a wszystkie mapowania typów muszą być zgodne z mapowaniami języka SQL usługi Azure Databricks.
  • Możesz zaimportować standardowe biblioteki języka Python dołączone przez usługę Azure Databricks, ale nie można dołączać bibliotek niestandardowych ani zależności zewnętrznych.
  • Jeśli nie określono wykazu lub schematu, funkcje zdefiniowane przez użytkownika języka Python są zarejestrowane w bieżącym aktywnym schemacie.
  • Funkcje zdefiniowane przez użytkownika języka Python są wykonywane w bezpiecznym, izolowanym środowisku i nie mają dostępu do systemów plików ani usług wewnętrznych.