簡體   English   中英

Firebase Google Apps 腳本上的數據庫機密

[英]Firebase Database Secrets on Google Apps Script

所以,首先,我問這個問題是因為我希望有人承認或否認 - 對我來說是一個神話 - 關於使用或不使用已棄用的 firebase 數據庫機密

為什么這個? 那么,在 Firebase 控制台的“服務帳戶”選項卡中,我可以看到:

數據庫機密目前已棄用並使用舊版 Firebase 令牌生成器。 使用 Firebase Admin SDK 更新您的源代碼

但在這個建議之下,我目前可以看到我的秘密密鑰 如果實際上已棄用此密鑰,為什么這是可能的?

但這個故事,並沒有就此結束。 如果使用 Google Apps 腳本搜索教程( 甚至在官方網站上),他們會使用已棄用的數據庫密鑰,但您可以閱讀以下內容:

谷歌警告說這種身份驗證方法已被棄用。 事實上,您仍然可以使用此方法,但標准服務帳戶更安全,建議使用。 由於數據庫機密更易於使用,遠未真正棄用並且對於大多數用例來說足夠安全,這就是我們將在此處使用的內容。

再說一次,這怎么可能?

我想說我已經嘗試過:

function myFunction() {
  var firebaseUrl = "https://myApp.firebaseio.com/";
  var secret = "theKey";
  var database = FirebaseApp.getDatabaseByUrl(firebaseUrl, secret);
  Logger.log(database.getData());
}

它有效,因為我看不到數據。 如果秘密存在,為什么? 這讓我想到允許使用密鑰,即使它已被棄用

有意見嗎?

所以我整整一年半之后遇到了這個問題,你是對的,關於將 Firebase 與 Apps Script 一起使用的信息已經過時且具有誤導性。 我想通了,正在嘗試更新 StackOverflow 和教程中的信息。

但這個故事,並沒有到此結束。 如果使用 Google Apps Script 搜索教程( 甚至在官方上),他們使用已棄用的數據庫密鑰,但您可以閱讀此...

您在此處添加的鏈接實際上是一個名為@RomainVialard的家伙的第 3 方網站 他的東西過去對我非常有用。 雖然他網站上的教程已經過時了,但他創建的庫仍然運行良好,並且最近才更新。


問題(服務器端) -對 OP 問題的回答

因此,對於服務器端部分,我使用官方的 OAuth2 庫帶有私鑰服務帳戶生成訪問令牌: https://console.firebase.google.com/u/0/project/<YOUR-PROJECT-ID>/settings/serviceaccounts/adminsdk : https://console.firebase.google.com/u/0/project/<YOUR-PROJECT-ID>/settings/serviceaccounts/adminsdk 然后我創建了一個從 oauth2 庫中檢索令牌的函數:

function getFirebaseService() {  
  return OAuth2.createService('Firebase')
      // Set the endpoint URL.
      .setTokenUrl('https://accounts.google.com/o/oauth2/token')

      // Set the private key and issuer. I stored mine in the PropertiesService... You could just use a variable somewhere.
      .setPrivateKey(fb_PRIVATE_KEY) //Service account private key
      .setIssuer(fb_SERVICE_EMAIL) //Service account email

      // Set the property store where authorized tokens should be persisted.
      .setPropertyStore(PropertiesService.getScriptProperties())

      // Set the scopes.
      .setScope('https://www.googleapis.com/auth/userinfo.email https://www.googleapis.com/auth/firebase.database');
}

使用此代碼,我可以調用getFirebaseService().getAccessToken()返回有效的“管理員”或編輯器級別的訪問令牌,可在 Firebase 調用中使用! 我使用 FirebaseApp 庫是因為它很簡單!

var service = getFirebaseService();
  if (service.hasAccess()) {
    var fb = FirebaseApp.getDatabaseByUrl(fb_URL, service.getAccessToken());
    //Success! Do what ever with Firebase!!

  } else {
    Logger.log("makeToken: " + service.getLastError());
  }

如果需要,您還可以生成客戶端身份驗證令牌以使用客戶端: FirebaseApp.getDatabaseByUrl(fb_URL, service.getAccessToken()).createAuthToken(USER_EMAIL); .


另一個常見問題(客戶端)

我必須克服的主要問題在我的問題,是火力地堡聯系SDK已經升級到3.x的如果您更新教程代碼以使用 3.x 版本,一切都會非常好!

// Initialize Firebase
var config = {
  apiKey: "<Web API Key>",
  authDomain: "<Project ID>.firebaseapp.com",
  databaseURL: "https://<DB URL>.firebaseio.com/"
  };

firebase.initializeApp(config);

//userRequestToken is retrieved from server-side Romain's FirebaseApp Library linked above.
firebase.auth().signInWithCustomToken(userRequestToken).catch(function(error) {
    // Handle Errors here.
    console.error("authClient: ", error.code, error.message);
  });

  return {
    uid: firebase.auth().currentUser.uid,
    metadata: {
      lastSignInTime: firebase.auth().currentUser.lastSignInTime
    }
  }; 

好吧,現在一些用戶已經對這個問題感興趣了 -一年多之后- 對這個問題(也考慮一下Chris W的回答),我發布了使用GSApp庫的方法,它也可以在沒有數據庫機密的情況下工作

  1. 安裝GSApp庫。 為此,請轉到“資源”選項卡,然后單擊“庫”並粘貼 libraryId: MJ5317VIFJyKpi9HCkXOfS0MLm9v2IJHf

  2. 創建服務帳戶:

    • 在您的開發者控制台中創建一個新的API 項目,或使用與您的腳本相關聯的一個。
    • 選擇API 和 Auth -> Credentials
    • 單擊“創建新客戶端 ID”
    • 選擇服務帳戶並生成新的 JSON 密鑰。
    • 單擊“創建客戶端 ID” JSON 密鑰將自動下載。
    • 單擊左側菜單中的“API”
    • 啟用您需要此服務帳戶訪問的任何 API。
  3. 復制下載的JSON 密鑰文件的內容並將其粘貼到您的腳本屬性中 為此,請轉到文件->項目屬性->腳本屬性選項卡。 屬性字段中輸入service_account (或者您想命名),並在字段中粘貼JSON 密鑰文件的所有內容

  4. 使用以下代碼作為示例:

     function myFunction() { var firebaseUrl = "https://YOUR-FIREBASE-PROJECT.firebaseio.com/"; var jsonKey = JSON.parse(PropertiesService.getScriptProperties().getProperty("service_account")); var key = jsonKey.private_key; var clientEmail = jsonKey.client_email; var serverToken = new GSApp.init(key, ['https://www.googleapis.com/auth/firebase.database', 'https://www.googleapis.com/auth/userinfo.email'], clientEmail); serverToken.addUser(clientEmail).requestToken(); var token = serverToken.getToken(clientEmail).token; var dataPath = 'YOUR-FIREBASE-DATA-PATH'; var options = {}; var result = UrlFetchApp.fetch( firebaseUrl + dataPath + '.json' + '?access_token=' + token, options).getContentText(); var data = JSON.parse(result); var keys = Object.keys(data); var sheetRow = []; var entryKeys; for (index in keys) { sheetRow = []; entryKeys = Object.keys(data[keys[index]]) for (i in entryKeys) { Logger.log(entryKeys[i]); } } }

您從 firebase 獲取數據作為json object ,這意味着您需要手動檢查所有對象的屬性(forEach, map, for ... of)

這是從 firebase 最新版本訪問數據庫秘密的明確解決方案的鏈接

我不這么認為,但可能有人仍然需要這方面的幫助。

如果你需要替換“pin to pin”已棄用的秘密,因為它的日落來了,我發現的最好方法是:

用這個來獲取數據庫

   let token = ScriptApp.getOAuthToken();
   let db = FirebaseApp.getDatabaseByUrl(dbUrl, token);

這將為當前用戶(正在運行的用戶或腳本名稱中的用戶正在運行)獲取令牌。 必須在https://console.firebase.google.com/project/<<projectName>>/settings/iam添加此用戶,您可以在其中設置所有者、編輯者、查看者等權限...

哦……規則……規則是你可能在秘密中使用的超級基本規則。

   {
        "rules": {
            ".read": false,
            ".write": false
        }
    }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM