2009-09-11 6 views
1

Je suis en train d'utiliser la bibliothèque HttpClient (pour appeler les points d'extrémité REST de l'API Facebook) pour obtenir une clé de session et de vérifier l'utilisateur ...Facebook: Obtenir Signature incorrecte (104) lors de l'obtention clé de session

mon code est ici:

RunWith(SpringJUnit4ClassRunner.class) 
@ContextConfiguration(locations = 
{ "classpath*:**/*applicationContext-test.xml" }) 
public class FacebookUserTest 
{ 
    final String API_KEY = "9e2568d68f182a2957878f3acedd9453"; 
    final String SECRET = "f1298956895d39110be92a672e0d2284"; 
    final String TOKEN = "aa0c41aa4532053e8d0097844ab9bc7d"; 
    final String LOGIN = "http://www.facebook.com/login.php"; 
    final String HOST = "http://www.facebook.com/restserver.php"; 

    private static Logger log = 
     LoggerFactory.getLogger(FacebookUserTest.class); 

    protected FacebookUser FacebookUser; 

    @Test 
    public void testFindUserBySessionKey() throws Exception 
    { 
     loginToFacebook(); 
     String sessionKey = getSessionKey(); 
    } 

    public void loginToFacebook() throws Exception 
    { 
     HttpClient client = new HttpClient(); 
     client.setParams(new HttpClientParams()); 
     client.setState(new HttpState()); 

     GetMethod get = new GetMethod(LOGIN + "?api_key=" + API_KEY 
      + "&v=1.0&auth_token=" + TOKEN); 

     // Get login screen 
     client.executeMethod(get); 

     // Post credentials to login 
     PostMethod post = new PostMethod(LOGIN); 
     post.addParameter(new NameValuePair("api_key", API_KEY)); 
     post.addParameter(new NameValuePair("v", "1.0")); 
     post.addParameter(new NameValuePair("auth_token", TOKEN)); 
     post.addParameter(new NameValuePair("email", "[email protected]")); 
     post.addParameter(new NameValuePair("pass", "password")); 
     client.executeMethod(post); 
    } 

    public String getSessionKey() throws Exception 
    { 
     HttpClient client = new HttpClient(); 

     // Obtain session key 
     String host = "http://www.facebook.com/restserver.php"; 
     String sessSecret = "false"; 
     String toMd = "api_key=" + API_KEY + "auth_token=" + TOKEN 
      + "format=xmlgenerate_session_secret=" + sessSecret 
      + "method=facebook.auth.getSessionv=1.0" + SECRET; 
     String md5 = Md5Utils.MD5(toMd); 

     PostMethod post = new PostMethod(HOST); 

     NameValuePair[] data = { 
      new NameValuePair("api_key", API_KEY), 
      new NameValuePair("auth_token", TOKEN), 
      new NameValuePair("format", "xml"), 
      new NameValuePair("generate_session_secret", SECRET), 
      new NameValuePair("method", "auth.getSession"), 
      new NameValuePair("sig", md5), new NameValuePair("v", "1.0") 
     }; 

     post.setRequestBody(data); 
     post.setRequestHeader("Content-Type", 
      "application/x-www-form-urlencoded"); 
     post.setRequestHeader("User-Agent", 
      "Facebook API PHP5 Client 1.1 (curl) 5"); 

     // execute method and handle any error responses. 
     client.executeMethod(post); 

     StringBuilder sb = new StringBuilder(); 
     byte[] b = new byte[4096]; 

     for (int n; (n = post.getResponseBodyAsStream().read(b)) != -1;) 
     { 
      sb.append(new String(b, 0, n)); 
     } 

     String sessionId = sb.toString(); 
     log.warn("Session Id: " + sessionId); 

     return sessionId; 
    } 
} 

Quand je lance mon test JUnit, voici ce qui est imprimé à partir de la console:

WARN : com.myapp.FacebookUserTest - Session Id: 

<?xml version="1.0" encoding="UTF-8"?> 
<error_response xmlns="http://api.facebook.com/1.0/" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://api.facebook.com/1.0/ 
    http://api.facebook.com/1.0/facebook.xsd"> 
    <error_code>104</error_code> 
    <error_msg>Incorrect signature</error_msg> 
    <request_args list="true"> 
     <arg> 
      <key>api_key</key> 
      <value>9e2568d68f182a2957878f3acedd9453</value> 
     </arg> 
     <arg> 
      <key>auth_token</key> 
      <value>aa0c41aa4532053e8d0097844ab9bc7d</value> 
     </arg> 
     <arg> 
      <key>format</key> 
      <value>xml</value> 
     </arg> 
     <arg> 
      <key>generate_session_secret</key> 
      <value>f1298956895d39110be92a672e0d2284</value> 
     </arg> 
     <arg> 
      <key>method</key> 
      <value>auth.getSession</value> 
     </arg> 
     <arg> 
      <key>sig</key> 
      <value>fcf80d658f35d66396ac521da7102782</value> 
     </arg> 
     <arg> 
      <key>v</key> 
      <value>1.0</value> 
      </arg> 
    </request_args> 
</error_response> 

pourrait-il être mon code MD5Utils:

public class Md5Utils 
{ 
     private static String convertToHex(byte[] data) 
     { 
      StringBuffer buf = new StringBuffer(); 
      for (int i = 0; i < data.length; i++) { 
       int halfbyte = (data[i] >>> 4) & 0x0F; 
       int two_halfs = 0; 
       do { 
        if ((0 <= halfbyte) && (halfbyte <= 9)) 
         buf.append((char) ('0' + halfbyte)); 
        else 
         buf.append((char) ('a' + (halfbyte - 10))); 
         halfbyte = data[i] & 0x0F; 
       } 
       while (two_halfs++ < 1); 
      } 
     return buf.toString(); 
     } 

    public static String MD5(String text) 
    throws NoSuchAlgorithmException, UnsupportedEncodingException { 
     MessageDigest md; 
     md = MessageDigest.getInstance("MD5"); 
     byte[] md5hash = new byte[32]; 
     md.update(text.getBytes("iso-8859-1"), 0, text.length()); 
     md5hash = md.digest(); 
     return convertToHex(md5hash); 
    } 
} 

Qu'est-ce que je fais de mal pour générer une signature incorrecte?

apprécierais vraiment si quelqu'un pouvait me aider ou me diriger dans la bonne direction ...

Bonne programmation et grâce à la lecture!

Répondre

0

Essayez cette

string GenerateSignature(IDictionary<string, string> parameters) 
    { 
     StringBuilder signatureBuilder = new StringBuilder(); 

     // Sort the keys of the method call in alphabetical order 
     List<string> keyList = ParameterDictionaryToList(parameters); 
     keyList.Sort(); 

     // Append all the parameters to the signature input paramaters 
     foreach (string key in keyList) 
      signatureBuilder.Append(String.Format(CultureInfo.InvariantCulture, "{0}={1}", key, parameters[key])); 

     // Append the secret to the signature builder 
     signatureBuilder.Append(ConfigurationManager.AppSettings["FBApiSecret"]); 

     MD5 md5 = MD5.Create(); 
     // Compute the MD5 hash of the signature builder 
     byte[] hash = md5.ComputeHash(Encoding.UTF8.GetBytes(signatureBuilder.ToString().Trim())); 

     // Reinitialize the signature builder to store the actual signature 
     signatureBuilder = new StringBuilder(); 

     // Append the hash to the signature 
     foreach (byte hashByte in hash) 
      signatureBuilder.Append(hashByte.ToString("x2", CultureInfo.InvariantCulture)); 

     return signatureBuilder.ToString(); 
    } 

    string CreateHTTPParameterList(IDictionary<string, string> parameterList) 
    { 
     StringBuilder queryBuilder = new StringBuilder(); 
     parameterList.Add("api_key", ConfigurationManager.AppSettings["FBApiKey"]); 
     parameterList.Add("v", "1.0"); 
     parameterList.Add("call_id", DateTime.Now.Ticks.ToString("x", CultureInfo.InvariantCulture)); 
     parameterList.Add("sig", GenerateSignature(parameterList)); 
     //parameterList.Add("sig", _sig); 

     // Build the query 
     foreach (KeyValuePair<string, string> kvp in parameterList) 
     { 
      queryBuilder.Append(kvp.Key); 
      queryBuilder.Append("="); 
      queryBuilder.Append(HttpUtility.UrlEncode(kvp.Value)); 
      queryBuilder.Append("&"); 
     } 
     queryBuilder.Remove(queryBuilder.Length - 1, 1); 

     return queryBuilder.ToString(); 
    } 

Exemple d'utilisation:

 Dictionary<string, string> parameterList = new Dictionary<string, string>(); 
     parameterList.Add("auth_token", authCode); 
     parameterList.Add("format", "json"); 
     parameterList.Add("method", "facebook.auth.getSession"); 

     string req = CreateHTTPParameterList(parameterList); 

I tryed à copier/coller ces codes de mon ancien projet. J'espère que cela vous sera utile.

+0

Votre code est en C# droite? – Arya

0

vous avez une erreur dans votre paramètre vous envoyez generate_session_secret votre code secret, il doit être vrai ou faux

vous définissez: nouvelle NameValuePair ("generate_session_secret", SECRET),

il y a conflit dans votre paramètre que vous avez mis en post et la signature

Questions connexes