Function Compute支援HTTP觸發器,配置HTTP觸發器的函數可以通過HTTP請求被觸發執行。此時函數可以看做一個Web Server,對HTTP請求進行處理,並將處理結果返回給調用端。本文介紹如何在Function Compute控制台配置HTTP觸發器並使用HTTP請求觸發。
前提條件
步驟一:建立觸發器
HTTP觸發器與其他類型的觸發器不同,當您建立HTTP類型的函數後,系統會預設為該函數建立一個HTTP觸發器,而對於其他類型的觸發器,需根據觸發源手動建立對應的觸發器。
- 登入Function Compute控制台,在左側導覽列,單擊服務及函數。
- 在頂部功能表列,選擇地區,然後在服務列表頁面,單擊目標服務。
- 在函數管理頁面,單擊建立函數。
在建立函數頁面,選擇使用內建運行時建立,然後根據需要,填寫函數相關資訊。
需設定的配置項說明如下,其餘配置項的值保持預設值即可。更多資訊,請參見建立函數。
配置項
解釋說明
配置項
解釋說明
基本設定
函數名稱
設定您要建立的函數的名稱。
請求處理常式類型
選擇處理 HTTP 要求。
觸發器配置(可選)
名稱
設定您要建立的觸發器的名稱。
要求方法
指定可以通過哪些方法觸發該HTTP觸發器。
禁用公網存取 URL
預設選擇否,即允許公網網域名稱訪問該觸發器。
如果選擇是,建立的HTTP觸發器將不提供預設的公網網域名稱。此時,如果通過公網網域名稱來調用函數,將會提示錯誤
access denied due to function internet URL is disabled
。通過自訂網域名的訪問,則不受影響。認證方式
選擇Function Compute對HTTP請求的認證方式。取值說明如下:
無需認證:無需對HTTP請求進行身份認證,支援匿名訪問,任何人可發起HTTP請求調用您的函數。
簽名認證:需要對HTTP請求進行身份認證。關於簽名認證的範例程式碼,請參見簽名認證。
JWT 認證:需要對HTTP請求進行JWT認證。更多資訊,請參見為HTTP觸發器配置JWT認證鑒權。
您可以根據需要對已建立的HTTP觸發器的配置項進行修改,包括版本或別名、要求方法、禁用公網存取 URL和認證方式。
步驟二:編寫並部署代碼
完成建立HTTP觸發器後,您可以開始編寫函數代碼。
在函數詳情頁面,單擊函數代碼頁簽,在代碼編輯器中編寫代碼,然後單擊部署代碼。
程式碼範例如下。
var getRawBody = require('raw-body')
module.exports.handler = function (request, response, context) {
// get request info
getRawBody(request, function (err, data) {
var params = {
path: request.path,
queries: request.queries,
headers: request.headers,
method: request.method,
body: data,
url: request.url,
clientIP: request.clientIP,
}
// you can deal with your own logic here
// set response
var respBody = new Buffer.from(JSON.stringify(params));
// var respBody = new Buffer( )
response.setStatusCode(200)
response.setHeader('content-type', 'application/json')
response.send(respBody)
})
};
# -*- coding: utf-8 -*-
import json
HELLO_WORLD = b"Hello world!\n"
def handler(environ, start_response):
request_uri = environ['fc.request_uri']
response_body = {
'uri':environ['fc.request_uri'],
'method':environ['REQUEST_METHOD']
}
# do something here
status = '200 OK'
response_headers = [('Content-type', 'text/json')]
start_response(status, response_headers)
# Python2
return [json.dumps(response_body)]
# Python3 tips: When using Python3, the str and bytes types cannot be mixed.
# Use str.encode() to go from str to bytes
# return [json.dumps(response_body).encode()]
<?php
use RingCentral\Psr7\Response;
function handler($request, $context): Response{
/*
$body = $request->getBody()->getContents();
$queries = $request->getQueryParams();
$method = $request->getMethod();
$headers = $request->getHeaders();
$path = $request->getAttribute("path");
$requestURI = $request->getAttribute("requestURI");
$clientIP = $request->getAttribute("clientIP");
*/
return new Response(
200,
array(
"custom_header1" => "v1",
"custom_header2" => ["v2", "v3"],
),
"hello world"
);
}
對於非同步呼叫,請在函數鏈路中做好非同步結果回調處理。具體操作,請參見結果回調。
步驟三:測試函數
方式一:使用控制台測試函數
同步調用
在函數詳情頁面,單擊函數代碼頁簽,然後單擊測試函數。
非同步呼叫
在函數詳情頁面,單擊測試函數頁簽,勾選我想通過非同步方式進行調用,然後單擊測試函數。
方式二:使用瀏覽器測試函數
將HTTP觸發器URL輸入瀏覽器地址欄,按斷行符號鍵執行。
執行完成後,瀏覽器中會返回執行結果檔案。
HTTP觸發器URL的擷取方式如下所示。
針對建立HTTP觸發器,推薦您使用Function Compute為建立HTTP觸發器分配的子網域名稱作為HTTP觸發器URL。
子網域名稱格式如下。
<subdomain>.<region_id>.fcapp.run/[action?queries]
樣本如下。
funcname-svcname-khljsjksld.cn-shanghai.fcapp.run/action?hello=world
您也可以按照存量HTTP觸發器URL組裝規則群組裝HTTP觸發器URL。Function Compute推薦您使用Function Compute為建立HTTP觸發器分配的子網域名稱
subdomain
作為HTTP觸發器URL進行函數測試,能有效避免404
報錯,也能避免代碼中耦合Function Compute的服務名稱和函數名稱,增強代碼的可移植性。關於404
報錯的更多資訊,請參見當我使用瀏覽器或cURL方式訪問函數時出現404怎麼辦?。針對存量HTTP觸發器,您可以按照組裝規則群組裝HTTP觸發器URL。
組裝規則如下。
<account_id>.<region_id>.fc.aliyuncs.com/<version>/proxy/<serviceName>/<functionName>/[action?queries]
樣本如下。
164901546557****.cn-shanghai.fc.aliyuncs.com/2016-08-15/proxy/serviceName/functionName/action?hello=world
參數說明如下。
參數
說明
參數
說明
account_id
阿里雲帳號ID。
您可以在安全設定中擷取您的帳號ID。如果您是RAM使用者,將滑鼠移至控制台右上方的頭像處,可以看到您的阿里雲帳號ID。
region_id
Function Compute服務所在的地區。
version
Function Compute的API版本。
serviceName
服務名稱。
functionName
函數名稱。
action
自訂的請求路徑。
queries
查詢參數。
方式三:使用cURL測試函數
同步調用
在命令列執行如下命令,執行完成後會返回執行結果。
curl -v https://http-***.cn-shenzhen.fcapp.run/$path
非同步呼叫
在命令列執行如下命令,執行完成後會返回Function Compute接收請求的結果。其中狀態代碼
202
表示請求成功,其餘表示請求出現錯誤,關於錯誤碼的解釋,請參見常見問題(錯誤排查)。curl -v -H "X-Fc-Invocation-Type: Async" https://http-***.cn-shenzhen.fcapp.run/$path
(可選)使用API Gateway保護HTTP函數
預設情況下,Function Compute不會對HTTP請求進行身分識別驗證,支援匿名訪問HTTP函數,即任何人都可以發送HTTP請求調用您的函數。為防止非法使用者訪問您的函數,引起不必要的資源浪費或安全隱患,您可以開啟身份認證的同時將HTTP函數與API Gateway進行對接,利用API Gateway的IP存取控制外掛程式、JWT認證外掛程式或BasicAuth外掛程式等保護您的HTTP函數。
在Function Compute控制台找到目標HTTP函數,在函數詳情頁面單擊觸發器管理頁簽,然後編輯HTTP觸發器,是否需要認證選擇為是。
登入API Gateway控制台,切換至HTTP函數所在地區。
建立分組。具體操作,請參見建立分組。
將您的網域名稱通過CNAME方式解析到API Gateway提供的次層網域上。具體操作,請參見CNAME綁定網域名稱。
建立API。
主要配置項設定如下,其餘配置項下的設定選擇預設值或者根據實際情況填寫即可。更多資訊,請參見建立 API。
安全認證:選擇無認證,後續會使用外掛程式進行認證。
請求Path:填寫根目錄/,然後選中匹配所有子路徑。
HTTP Method:選擇ANY。
入參請求模式:選擇入參透傳。
後端服務類型:選擇Function Compute。
函數類型:選擇HTTP函數。
觸發器路徑:填寫Function Compute的HTTP函數的內網訪問地址。
ContentType:選擇透傳用戶端ContentType頭。
發布API。單擊已建立的API右側操作列的發布,選擇線上環境,然後單擊發布。
建立一個類型為後端簽名的外掛程式,
key
和value
分別配置為您的阿里雲帳號的AccessKey ID
和AccessKey Secret
。然後綁定您剛才建立的API。具體操作,請參見外掛程式概述。
完成以上步驟後,您可以通過自己的網域名稱訪問HTTP函數。您還可以建立以下外掛程式,並將其綁定到您的API,保護您的HTTP函數。
常見問題
為什麼HTTP函數無法執行?
如果是新建立的觸發器,會有10s左右的緩衝更新時間,請稍後再試。
請檢查函數的入口函數是否正確,HTTP函數與普通函數的入口函數不同。不同語言的HTTP函數請參見以下文檔:
為什麼函數無法結束?
請檢查是否調用返回函數。
Node.js需調用
response.send()
。Python需調用
return
。PHP需調用
return new Response()
。Java需調用
HttpServletResponse
C#需調用
return
。Custom Runtime以各語言樣本為準。
錯誤排查
錯誤主要分為以下兩種。
請求錯誤是指發送的Request不符合標準,在Response裡報錯狀態代碼為4xx。
函數錯誤即編寫的函數有問題,會報5xx狀態代碼。
下表描述請求錯誤和函數錯誤可能出現的情境,以便您迅速排查問題。
錯誤類型 | X-Fc-Error-Type | HTTP狀態代碼 | 原因分析 | 是否計費 |
錯誤類型 | X-Fc-Error-Type | HTTP狀態代碼 | 原因分析 | 是否計費 |
請求錯誤 | FcCommonError | 400 | 您的請求超過Request限制項的限制。更多資訊,請參見HTTP觸發器概述。 | 否 |
FcCommonError | 400 | 調用需要身份認證的函數的Request沒有傳入Date資訊或Authorization資訊。 | 否 | |
FcCommonError | 403 | 調用需要身份認證的函數的Request的簽名錯誤,即Authorization不正確。由於Date參與簽名計算,且超過15 min,簽名失效,一種常見的原因是使用需要訪問認證的HTTP觸發器,Request header中發送的Date距目前時間超過15 min,導致簽名失效。 | 否 | |
FcCommonError | 403 | 您的Request請求使用HTTP觸發器中未配置的要求方法。例如,HTTP觸發器中的要求方法只配置GET方法,卻發送POST方法的HTTP請求。 | 否 | |
FcCommonError | 404 | 向沒有設定HTTP觸發器的函數發送HTTP請求。 | 否 | |
使用者流控 | FcCommonError | 429 | 使用者被流控,可減小並發量或者聯絡Function ComputeTeam Dev提高並發度。 | 否 |
函數錯誤 | UnhandledInvocationError | 502 | 函數的傳回值超過Response限制項的限制。更多資訊,請參見HTTP觸發器概述。 | 是 |
UnhandledInvocationError | 502 | 函數代碼有語法錯誤或者異常。 | 是 | |
UnhandledInvocationError | 502 | 向未使用HTTP入口函數的函數發送HTTP請求。 | 是 | |
系統錯誤 | FcCommonError | 500 | Function Compute系統錯誤,可重試解決。 | 否 |
系統流控 | FcCommonError | 503 | Function Compute系統流控。可用指數退避方式重試。 | 否 |
如果問題還未能解決,請加入DingTalk使用者群(DingTalk群號:64970014484),聯絡Function Compute工程師即時溝通處理。
更多資訊
除了Function Compute控制台,您還可通過以下方式配置觸發器:
通過Serverless Devs工具配置觸發器。更多操作,請參見Serverless Devs。
通過SDK配置觸發器。更多操作,請參見SDK列表。
如需對建立的觸發器進行修改或刪除,具體操作,請參見觸發器管理。