Spanner 원격 함수를 사용하면 SQL 이외의 언어로 함수를 구현할 수 있습니다. 함수는 Cloud Run Functions 또는 Cloud Run에서 호스팅되어야 합니다. 이러한 방식으로 함수를 호스팅하면 복잡한 비즈니스 로직을 별도의 원격 함수로 분할할 수 있습니다.
일반적인 원격 함수 배포에는 다음 단계가 포함됩니다.
Cloud Run Functions 또는 Cloud Run에서 HTTPS 엔드포인트를 만듭니다.
- 원격 함수를 처음 사용하는 경우 Cloud Run Functions를 사용하는 것이 좋습니다.
해당 HTTPS 엔드포인트를 가리키는 Spanner의 원격 함수를 만듭니다.
쿼리에서 원격 함수를 사용합니다.
필요한 역할
Spanner 에이전트 서비스 계정 (service-PROJECT_ID@gcp-sa-spanner.iam.gserviceaccount.com)에 Spanner 원격 함수를 사용하는 데 필요한 권한이 있는지 확인하려면 관리자에게 Spanner 에이전트 서비스 계정 (service-PROJECT_ID@gcp-sa-spanner.iam.gserviceaccount.com)에 프로젝트에 대한 Spanner API 서비스 에이전트 (roles/spanner.serviceAgent) IAM 역할을 부여해 달라고 요청하세요.
관리자가 Spanner 에이전트 서비스 계정 (service-PROJECT_ID@gcp-sa-spanner.iam.gserviceaccount.com)에 커스텀 역할 또는 기타 사전 정의된 역할을 통해서도 필요한 권한이 제공됩니다.
지원되는 유형
원격 함수는 다음 데이터 유형을 인수 또는 반환 유형으로 지원합니다.
ARRAY(지원되는 다음 유형 중 하나)BOOLEANBYTESDATEJSONINTEGERNUMERICSTRINGTIMESTAMP
제한사항
테이블 값 원격 함수는 만들 수 없습니다.
생성된 열 표현식에서는 원격 함수가 지원되지 않습니다.
일시적인 네트워크 오류 또는 Spanner 내부 재시작으로 인해 응답이 성공한 후에도 엔드포인트에 동일한 데이터가 포함된 반복 요청이 표시될 수 있습니다.
부분 Spanner 인스턴스에서 원격 함수를 실행하는 것은 지원되지 않습니다.
커스텀 도메인 뒤에 있는 Cloud Run Functions에는 원격 함수가 지원되지 않습니다.
PostgreSQL 언어에서는 원격 함수가 지원되지 않습니다.
엔드포인트 만들기
비즈니스 로직은 Cloud Run 함수 또는 Cloud Run으로 구현해야 합니다. 엔드포인트는 단일 HTTPS POST 요청에서 행 배치를 처리하고 배치 결과를 HTTPS 응답으로 반환할 수 있어야 합니다.
BigQuery용 원격 함수를 만든 경우 Spanner에서 재사용할 수 있습니다.
Cloud Run 함수를 작성, 배포, 테스트, 유지보수하는 방법은 Cloud Run 함수 튜토리얼 및 기타 Cloud Run 함수 문서를 참고하세요.
Cloud Run 서비스를 작성, 배포, 테스트, 유지보수하는 방법은 Cloud Run 빠른 시작 및 기타 Cloud Run 문서를 참고하세요.
Cloud Run 함수 또는 Cloud Run 서비스의 기본 인증을 유지하는 것이 좋습니다. 인증되지 않은 호출을 허용하도록 서비스를 구성하지 마세요.
입력 형식
Spanner는 다음 형식으로 JSON 본문을 사용해서 HTTPS POST 요청을 전송합니다.
| 필드 이름 | 설명 | 입력란 유형 |
|---|---|---|
requestId
|
요청 식별자입니다. GoogleSQL 쿼리에서 엔드포인트로 전송되는 여러 요청들 간에 고유합니다. | 항상 제공됩니다. 문자열. |
calls
|
입력 데이터의 배치입니다. | 항상 제공됩니다. JSON 배열입니다.
각 요소는 단일 원격 함수 호출의 JSON 인코딩 인수 목록을 나타내는 JSON 배열입니다. |
요청 예시:
// Sample request to a Cloud Run functions to calculate sum of two numbers. This request
// has two calls batched together into a single request.
{
"requestId": "124ab1c",
"calls": [
[1, 2],
[3, 4]
]
}
출력 형식
Spanner에서는 엔드포인트가 다음 형식으로 HTTPS 응답을 반환할 것으로 예상됩니다. 그렇지 않으면 Spanner가 응답을 사용할 수 없고 원격 함수를 호출하는 쿼리가 실패합니다.
| 필드 이름 | 설명 | 값 범위 |
replies
|
반환 값의 배치입니다. | JSON 배열입니다.
각 요소는 외부 함수의 JSON 인코딩 반환 값에 해당합니다. 배열 크기는 HTTPS 요청에서calls의 JSON 배열 크기와 일치해야 합니다. 예를 들어 calls에서 JSON 배열에 4개 요소가 있으면 이 JSON 요소에도 4개 요소가 있어야 합니다. 성공적인 응답을 위해 필요합니다.
|
errorMessage
|
200 이외의 HTTPS 응답 코드가 반환될 때의 오류 메시지입니다. 재시도할 수 없는 오류의 경우 Spanner는 사용자에게 이 오류 메시지를 반환합니다. 실패한 응답에 필요합니다. 일반적으로 1KB 미만입니다. | 문자열. |
성공적인 응답의 예시:
// Sample response from the Cloud Run functions which has the sum of the two numbers. Note
// that the order of the values within `replies` field matches the `calls` field from
// the request.
{
"replies": [
3, // 1 + 2 = 3
7 // 3 + 4 = 7
]
}
실패한 응답의 예시:
{
// The error message returned by your Cloud Run functions to indicate an error.
// In this sample, the error message states that an overflow occurred when summing two numbers.
"errorMessage": "Overflow detected when calculating sum of two numbers."
}
HTTPS 응답 코드
엔드포인트가 성공적으로 응답하면 200 HTTPS 코드를 반환합니다. Spanner에서 다른 값을 수신하면 응답을 실패로 간주하고 HTTPS 응답 코드가 408, 429, 500, 503 또는 504이면 내부 제한에 도달할 때까지 재시도합니다.
샘플 코드
Cloud Run 함수
다음 샘플 Python 코드는 원격 함수의 모든 정수 인수 추가를 구현합니다. 일괄 호출의 인수를 사용해서 요청을 처리하고 모든 결과를 응답에 반환합니다.
"""
Python script which uses Flask framework to spin up a HTTP server to take
integers and return their sum. In case of overflow, it returns the error
as part of the response.
"""
import functions_framework
from flask import jsonify
# Max INT64 value encoded as a number in JSON by TO_JSON_STRING. Larger values are encoded as
# strings.
_MAX_LOSSLESS=9007199254740992
@functions_framework.http
def batch_add(request):
try:
return_value = []
request_json = request.get_json()
calls = request_json['calls']
for call in calls:
return_value.append(sum([int(x) if isinstance(x, str) else x for x in call if x is not None]))
replies = [str(x) if x > _MAX_LOSSLESS or x < -_MAX_LOSSLESS else x for x in return_value]
return_json = jsonify( { "replies": replies } )
return return_json
except Exception as e:
return jsonify( { "errorMessage": str(e) } ), 400
함수가 us-east1 리전의 PROJECT_ID
프로젝트에 함수 이름 remote_add로 배포되었다고 가정하면 엔드포인트 https://us-east1-PROJECT_ID.cloudfunctions.net/remote_add를 사용하여 함수에 액세스할 수 있습니다.
Cloud Run
다음 샘플 Python 코드는 동일한 기능을 위해 Cloud Run에 빌드하고 배포할 수 있는 웹 서비스를 구현합니다.
"""
Python script which uses Flask framework to spin up a HTTP server to take
integers and return their sum. In case of overflow, it returns the error
as part of the response.
"""
import os
from flask import Flask, request, jsonify
# Max INT64 value encoded as a number in JSON by TO_JSON_STRING. Larger values are encoded as
# strings.
_MAX_LOSSLESS=9007199254740992
app = Flask(__name__)
@app.route("/", methods=['POST'])
def batch_add():
try:
return_value = []
request_json = request.get_json()
calls = request_json['calls']
for call in calls:
return_value.append(sum([int(x) if isinstance(x, str) else x for x in call if x is not None]))
replies = [str(x) if x > _MAX_LOSSLESS or x < -_MAX_LOSSLESS else x for x in return_value]
return jsonify( { "replies" : replies } )
except Exception as e:
return jsonify( { "errorMessage": str(e) } ), 400
if __name__ == "__main__":
app.run(debug=True, host="0.0.0.0", port=int(os.environ.get("PORT", 8080)))
코드를 빌드하고 배포하려면 빠른 시작: Python(Flask) 웹 앱을 빌드하고 Cloud Run에 배포를 참고하세요.
Cloud Run 서비스가 us-east1 리전의 PROJECT_ID 프로젝트에 서비스 이름 remote_add로 배포되었다고 가정하면 https://remote_add-<project_id_hash>-ue.a.run.app 엔드포인트를 사용하여 이 서비스에 액세스할 수 있습니다.
원격 함수 만들기
원격 함수를 만들려면 다음 단계를 따르세요.
SQL
Spanner에서 다음 CREATE FUNCTION 문을 실행합니다.
CREATE FUNCTION REMOTE_FUNCTION_NAME(x INT64, y INT64) RETURNS INT64 NOT DETERMINISTIC LANGUAGE REMOTE OPTIONS (
endpoint = `ENDPOINT_URL`,
max_batching_rows = MAX_BATCHING_ROWS
);
다음을 바꿉니다.
REMOTE_FUNCTION_NAME: 원격 함수의 이름입니다. 예를 들면sum_func입니다.ENDPOINT_URL: 이전 단계에서 만든 Cloud Run 함수 또는 Cloud Run 엔드포인트MAX_BATCHING_ROWS(선택사항): 요청의 일부로 전송할 최대 행 수입니다. 지정하지 않으면 Spanner에서 배치 크기를 자동으로 결정합니다.
쿼리에서 원격 함수 사용
쿼리 내에서 이전 단계의 원격 함수를 호출하려면 다음 예시를 사용하세요.
SELECT REMOTE_FUNCTION_NAME(1, 2); -- 1 + 2 = 3
가격 책정
표준 Spanner 가격 책정이 적용됩니다.
Spanner는 Cloud Run Functions 또는 Cloud Run으로 전송되거나 Cloud Run Functions 또는 Cloud Run에서 수신된 바이트에 대해 청구합니다.
이 기능을 사용하면 Cloud Run Functions 및 Cloud Run에서 비용이 발생할 수 있습니다. 자세한 내용은 Cloud Run Functions 및 Cloud Run 가격 책정 페이지를 참고하세요.