2010-11-30 46 views
3

當用戶使用FB.login()調用顯示的彈出窗口登錄Facebook時,JS SDK植入我的域中一個包含純文本oauth access_token的cookie。然後,這個cookie隨着後續的請求被髮送到我的服務器 - 很明顯,並非每個請求都使用httpsFacebook JS SDK:純文本和安全性的access_token

這不是一個安全問題嗎?如果是的話,那麼如何解決呢?

回答

2

的攻擊者是誰能夠嗅探網絡流量(例如,無線lan),可以讀取cookie。並假裝成爲它創建的人。

這不是一個真正的問題,因爲相同的攻擊在Facebook頁面上工作:只有用戶名/密碼 - 身份驗證通過https完成。以下所有頁面均使用未加密的http,其中包含cookie。

有一個易於使用的Firefox擴展,它允許鋼化餅乾,如果你能嗅探網絡流量:http://codebutler.com/firesheep

PS:stackoverflow.com是脆弱的,太。

3

這不是問題,因爲您可以驗證cookie的真實性。 Facebook包含一個名爲sig的值,每個cookie。我不會詳細介紹,但基本上,您可以將API祕密附加到cookie中,刪除sig值,對cookie值進行散列並驗證散列值是否與sig相匹配。因爲你和Facebook是唯一知道API祕密價值的人,所以你可以確定這個cookie沒有被篡改。

事情的另一方,查看cookie內容的用戶也無關緊要。該cookie只包含與該用戶關聯的訪問令牌。如果用戶試圖篡改cookie,唯一會發生的是他們會使cookie無效。無論如何,他們的訪問令牌只能讓他們訪問自己的帳戶。

最重要的是驗證cookie是真實的。許多人不這樣做,並造成巨大的安全問題。例如,該cookie包含Facebook用戶標識。說我得到那個用戶ID然後問我的用戶他們的信用卡。如果我將該信用卡與該用戶ID一起存儲,但不驗證該cookie,任何人都可以進入並更改該cookie中的用戶標識值並訪問私人數據。然而,如果我用API祕密驗證cookie,我會知道cookie是否被篡改。

下面是我們如何驗證的cookie在我的Facebook C#SDK(http://facebooksdk.codeplex.com):

 /// <summary> 
     /// Validates a session_version=3 style session object. 
     /// </summary> 
     /// <param name="session">The session to validate.</param> 
     protected override void ValidateSessionObject(FacebookSession session) 
     { 
      if (session == null) 
      { 
       return; 
      } 

      var signature = this.GenerateSignature(session); 
      if (session.Signature == signature.ToString()) 
      { 
       return; 
      } 

      session = null; 
     } 

     /// <summary> 
     /// Generates a MD5 signature for the facebook session. 
     /// </summary> 
     /// <param name="session">The session to generate a signature.</param> 
     /// <returns>An MD5 signature.</returns> 
     /// <exception cref="System.ArgumentNullException">If the session is null.</exception> 
     /// <exception cref="System.InvalidOperationException">If there is a problem generating the hash.</exception> 
     protected override string GenerateSignature(FacebookSession session) 
     { 
      var args = session.Dictionary; 
      StringBuilder payload = new StringBuilder(); 
      var parts = (from a in args 
         orderby a.Key 
         where a.Key != "sig" 
         select string.Format(CultureInfo.InvariantCulture, "{0}={1}", a.Key, a.Value)).ToList(); 
      parts.ForEach((s) => { payload.Append(s); }); 
      payload.Append(this.ApiSecret); 
      byte[] hash = null; 
      using (var md5 = System.Security.Cryptography.MD5CryptoServiceProvider.Create()) 
      { 
       if (md5 != null) 
       { 
        hash = md5.ComputeHash(Encoding.UTF8.GetBytes(payload.ToString())); 
       } 
      } 

      if (hash == null) 
      { 
       throw new InvalidOperationException("Hash is not valid."); 
      } 

      StringBuilder signature = new StringBuilder(); 
      for (int i = 0; i < hash.Length; i++) 
      { 
       signature.Append(hash[i].ToString("x2", CultureInfo.InvariantCulture)); 
      } 

      return signature.ToString(); 
     } 
+0

攻擊是複製別人的cookie並假裝成爲受害者。所以驗證它會證實它是有效的。 – 2010-12-01 06:51:59

+0

我的意思是`nhnb`寫了什麼,但我也很感謝你的回答。 – 2010-12-01 12:09:23