https.onCall 的協議規範

一個https.onCall雲函數觸發是HTTPS觸發與請求和響應一個特定的格式。本節提供了客戶端 SDK 用於實現 API 的 HTTPS 請求和響應格式的規範。如果使用 Android、Apple 平台或 Web SDK 無法滿足您的要求,此信息可能對您有用。

請求格式:headers

該HTTP請求到一個可調用觸發端點必須是POST具有以下標題:

  • 要求: Content-Type: application/json
    • 可選; charset=utf-8是允許的。
  • 可選: Authorization: Bearer <token>
    • 發出請求的登錄用戶的 Firebase 身份驗證用戶 ID 令牌。後端自動驗證此令牌,並使得它在處理程序的可用的context 。如果令牌無效,則拒絕請求。
  • 可選: Firebase-Instance-ID-Token: <iid>
    • 來自 Firebase 客戶端 SDK 的 FCM 註冊令牌。這必須是一個字符串。這是在處理器的使用context 。它用於定位推送通知。
  • 可選: X-Firebase-AppCheck: <token>
    • 發出請求的客戶端應用程序提供的 Firebase App Check 令牌。後端自動驗證該令牌並對其進行解碼,注入appId在處理程序的context 。如果無法驗證令牌,則拒絕請求。 (適用於 SDK >=3.14.0)

如果包含任何其他標頭,則請求將被拒絕,如下面的響應文檔中所述。

注:在JavaScript客戶端,這些請求觸發CORS OPTIONS預檢,這是因為:

  • application/json是不允許的。它必須是text/plainapplication/x-www-form-urlencoded
  • Authorization報頭是不是一個CORS-safelisted請求頭
  • 同樣不允許使用其他標題。

可調用觸發自動處理這些OPTIONS請求。

請求正文

HTTP 請求的主體應該是具有以下任何字段的 JSON 對象:

  • 要求: data -傳遞給函數的參數。這可以是任何有效的 JSON 值。這會根據下面描述的序列化格式自動解碼為原生 JavaScript 類型。

如果請求中存在任何其他字段,則後端認為請求格式錯誤,並被拒絕。

響應格式:狀態碼

有幾種情況下,可能會導致不同的HTTP狀態碼和串狀態碼錯誤的響應。

  1. 在之前的HTTP錯誤的情況下client被調用觸發,響應不為客戶端功能來處理。例如,如果客戶端試圖調用一個不存在的功能,它接收到一個404 Not Found響應。

  2. 如果客戶端觸發被調用,但該請求是在錯誤的格式,例如無法JSON,具有無效字段,或丟失的data字段,該請求被拒絕, 400 Bad Request ,並帶有錯誤代碼INVALID_ARGUMENT

  3. 如果令牌請求中提供的身份驗證是無效的,則請求被拒絕, 401 Unauthorized ,並帶有錯誤代碼UNAUTHENTICATED

  4. 如果請求中提供的 FCM 註冊令牌無效,則行為未定義。不會對每個請求都檢查令牌,除非它用於通過 FCM 發送推送通知。

  5. 如果可贖回觸發被調用,但未能與未處理的異常或返回失敗的承諾,該請求被拒絕, 500 Internal Server Error ,並帶有錯誤代碼INTERNAL 。這可以防止編碼錯誤意外地暴露給最終用戶。

  6. 如果調用可調用函數並使用為可調用函數提供的 API 返回顯式錯誤條件,則請求失敗。返回的HTTP狀態代碼是基於錯誤狀態到HTTP狀態正式映射,如在定義code.proto 。返回的特定錯誤代碼、消息和詳細信息在響應正文中進行編碼,詳情如下。這意味著,如果該函數返回狀態的明確的錯誤OK ,那麼響應狀態具有200 OK ,但error字段在響應中設置。

  7. 如果客戶觸發成功,則響應狀態為200 OK

響應格式:標題

響應具有以下標頭:

  • Content-Type: application/json
  • 可選; charset=utf-8是允許的。

響應體

來自客戶端端點的響應始終是 JSON 對象。它至少包含兩種resulterror ,與任何可選字段一起。如果響應不是一個JSON對象,或者不包含dataerror ,為失敗與谷歌的錯誤代碼,客戶端SDK應該把請求INTERNAL (13)

  • error -如果這個字段存在,則該請求被認為失敗,無論該HTTP狀態代碼或是否data也存在。該字段的值應在標準JSON對象谷歌雲HTTP映射格式錯誤,與字段statusmessage ,和(可選地) details 。該code字段不包括在內。如果status字段未設置,或者是無效的值,客戶端應該把地位INTERNAL ,按照code.proto 。如果details出現,它被包含在,連接到錯誤的客戶端SDK如果有任何用戶信息。
    注: details在此領域的用戶提供價值。它不一定是原癌類型鍵入作為谷歌的值列表Status格式。
  • result -由函數返回的值。這可以是任何有效的 JSON 值。 firebase-functions SDK 會自動將用戶返回的值編碼為這種 JSON 格式。客戶端 SDK 根據下面描述的序列化格式自動將這些參數解碼為原生類型。

如果存在其他字段,則應忽略它們。

序列化

任意數據負載的序列化格式對於請求和響應都是相同的。

對於平台的一致性,這些被編碼在JSON,就好像它們是一的值Any一個proto3協議緩衝器字段中,使用標準JSON映射。簡單的類型,如值nullintdouble ,或string直接編碼,不包括其顯式類型。因此,一個floatdouble編碼以同樣的方式,你可能不知道這是在通話的另一端接收。對於非 JSON 原生的類型,使用值的類型化 proto3 編碼。欲了解更多信息,請參閱所有JSON編碼的文檔

允許以下類型:

  • 空- null
  • INT(有符號或無符號的,最多32個比特) -例如3-30
  • 浮-例如3.14
  • 雙-例如3.14
  • 布爾值- truefalse
  • 字符串-如"hello world"
  • 地圖-例如, {"x": 3}
  • 列表-例如[1, 2, 3]
  • 長(有符號或無符號,最多 64 位) - [詳情見下文]

NaNInfinity的價值floatdouble不被支持。

需要注意的是long是一種特殊類型通常不允許在JSON,而是由proto3規範覆蓋。例如,這些編碼為:

{
    '@type': 'type.googleapis.com/google.protobuf.Int64Value',
    'value': '-123456789123456'
}

無符號長

{
    '@type': 'type.googleapis.com/google.protobuf.UInt64Value',
    'value': '123456789123456'
}

在一般情況下, @type重點應考慮保留,不用於傳入地圖。

因為沒有為簡單類型指定類型,所以一些值在通過連線後會改變類型。一個float在通過成為double 。一個short成為int ,等等。在Android中,這兩個ListJSONArray都支持列表值。在這種情況下,通過在JSONArray將產生一個List

如果有一個未知的地圖@type場進行反序列化,這是留給作為一個地圖。這允許開發人員在不破壞舊客戶端的情況下向其返回值添加具有新類型的字段。

代碼示例

本節中的示例說明瞭如何對以下內容進行編碼:

  • Swift 中的 callable.call 示例
  • 呼叫的成功響應
  • 呼叫的失敗響應

Swift 中的 Callable.call 示例進行編碼

callable.call([
    "aString": "some string",
    "anInt": 57,
    "aFloat": 1.23,
    "aLong": -123456789123456 as Int64
])

請求頭:

Method: POST
Content-Type: application/json; charset=utf-8
Authorization: Bearer some-auth-token
Firebase-Instance-ID-Token: some-iid-token

請求正文:

{
    "data": {
        "aString": "some string",
        "anInt": 57,
        "aFloat": 1.23,
        "aLong": {
            "@type": "type.googleapis.com/google.protobuf.Int64Value",
            "value": "-123456789123456"
        }
    }
}

編碼響應

return {
    "aString": "some string",
    "anInt": 57,
    "aFloat": 1.23
};

成功的響應頭:

200 OK
Content-Type: application/json; charset=utf-8

成功響應體:

{
    "response": {
        "aString": "some string",
        "anInt": 57,
        "aFloat": 1.23
    }
}

編碼失敗響應

throw new HttpsError("unauthenticated", "Request had invalid credentials.", {
  "some-key": "some-value"
});

失敗的響應頭:

401 UNAUTHENTICATED
Content-Type: application/json; charset=utf-8

失敗的響應體:

{
    "error": {
        "message": "Request had invalid credentials.",
        "status": "UNAUTHENTICATED",
        "details": {
            "some-key": "some-value"
        }
    }
}