2015-10-10 13 views
15

RSA Özel Anahtarı kullanılarak imzalanan ve RSA ortak anahtarıyla sunucu ucunda doğrulanan OAuth1 isteğinin kimliğini doğrulamak için bir kullanım durumum var.OAuth1a imzalanmış isteğini RSA-SHA1 ile Twitter joauth kullanarak doğrula?

Oauth imzalı istekleri doğrulama/doğrulama konusunda bize yardımcı olan bu kitaplığı Twitter'dan buldum. https://github.com/twitter/joauth

Bu kitaplığı Jersey veya Spring MVC eylem yönteminden doğrulamak için bu kitaplıktan yararlanmak istiyorum. Müşteriden gelen istek özel anahtar kullanılarak imzalanmış olurdu. Sonunda, isteği doğrulamak için istemcinin ortak anahtarını kullanırdım. RSA-SHA1 algo anlamına gelir.

Heyecan joauth yararlı olduğu görünüyor ama kütüphane okuma-me dosya tesisi olarak bu önerir ama javax.servlet.http.HttpServletRequest yapan bir kod bulamadık OAuthRequest

için HttpServletRequest dönüştürecektir kodu Eksik ->com.twitter.joauth.OAuthRequest dönüşüm.

İstek doğrulama, aşağıdaki imzası olan doğrulama yönteminde gerçekleşir. yöntem String parametre alır doğrulamak zaman

public VerifierResult verify(UnpackedRequest.OAuth1Request request, String tokenSecret, String consumerSecret); 

İkincisi ben de kullanılacak en uygun yolu olan bilmek istiyorum/twitter joauth ile RSA açık anahtar okumak?

+0

Hangi JOAuth sürümünü kullanıyorsunuz? – Val

cevap

1

Twitter yoluyla kullanıcıların kimliklerini doğrulamak için hiçbir zaman kitaplık kullanmamıştım. Ama ben sadece UnpackedRequest.OAuth1Request'e baktım. Tüm parametreleri doldurarak bu sınıfın bir örneğini oluşturabilirsiniz. Twitter OAuth Üstbilgisi yaratıcısını yazdım, böylece bu parametreleri doldurmak veya POST isteklerini doğrudan kitaplık olmadan göndermek için kullanabilirsiniz.

İşte bütün sınıfları neye ihtiyacınız:

İmza - OAth İmza oluşturmak için.

public class Signature { 
    private static final String HMAC_SHA1_ALGORITHM = "HmacSHA1"; 
    public static String calculateRFC2104HMAC(String data, String key) 
      throws java.security.SignatureException 
    { 
     String result; 
     try { 
      SecretKeySpec signingKey = new SecretKeySpec(key.getBytes(), HMAC_SHA1_ALGORITHM); 
      Mac mac = Mac.getInstance(HMAC_SHA1_ALGORITHM); 
      mac.init(signingKey); 
      byte[] rawHmac = mac.doFinal(data.getBytes()); 
      result = new String(Base64.encodeBase64(rawHmac)); 
     } catch (Exception e) { 
      throw new SignatureException("Failed to generate HMAC : " + e.getMessage()); 
     } 
     return result; 
    } 
} 

NvpComparator - başlıkta ihtiyaç parametreleri sıralamak için.

public class NvpComparator implements Comparator<NameValuePair> { 
    @Override 
    public int compare(NameValuePair arg0, NameValuePair arg1) { 
     String name0 = arg0.getName(); 
     String name1 = arg1.getName(); 
     return name0.compareTo(name1); 
    } 
} 

OAuth - URL kodlamak için.

class OAuth{ 
... 
    public static String percentEncode(String s) { 
      return URLEncoder.encode(s, "UTF-8") 
        .replace("+", "%20").replace("*", "%2A") 
        .replace("%7E", "~"); 
    } 
... 
} 

HeaderCreator - tüm gerekli parametreleri oluşturmak ve OAth başlık param üretmek için.

public class HeaderCreator { 
    private String authorization = "OAuth "; 
    private String oAuthSignature; 
    private String oAuthNonce; 
    private String oAuthTimestamp; 
    private String oAuthConsumerSecret; 
    private String oAuthTokenSecret; 

    public String getAuthorization() { 
     return authorization; 
    } 

    public String getoAuthSignature() { 
     return oAuthSignature; 
    } 

    public String getoAuthNonce() { 
     return oAuthNonce; 
    } 

    public String getoAuthTimestamp() { 
     return oAuthTimestamp; 
    } 

    public HeaderCreator(){} 

    public HeaderCreator(String oAuthConsumerSecret){ 
     this.oAuthConsumerSecret = oAuthConsumerSecret; 
    } 

    public HeaderCreator(String oAuthConsumerSecret, String oAuthTokenSecret){ 
     this(oAuthConsumerSecret); 
     this.oAuthTokenSecret = oAuthTokenSecret; 
    } 

    public String getTwitterServerTime() throws IOException, ParseException { 
     HttpsURLConnection con = (HttpsURLConnection) 
       new URL("https://api.twitter.com/oauth/request_token").openConnection(); 
     con.setRequestMethod("HEAD"); 
     con.getResponseCode(); 
     String twitterDate= con.getHeaderField("Date"); 
     DateFormat formatter = new SimpleDateFormat("EEE, dd MMM yyyy HH:mm:ss Z", Locale.ENGLISH); 
     Date date = formatter.parse(twitterDate); 
     return String.valueOf(date.getTime()/1000L); 
    } 

    public String generatedSignature(String url, String method, List<NameValuePair> allParams, 
            boolean withToken) throws SignatureException { 
     oAuthNonce = String.valueOf(System.currentTimeMillis()); 
     allParams.add(new BasicNameValuePair("oauth_nonce", oAuthNonce)); 
     try { 
      oAuthTimestamp = getTwitterServerTime(); 
      allParams.add(new BasicNameValuePair("oauth_timestamp", oAuthTimestamp)); 
     }catch (Exception ex){ 
      //TODO: Log!! 
     } 

     Collections.sort(allParams, new NvpComparator()); 
     StringBuffer params = new StringBuffer(); 
     for(int i=0;i<allParams.size();i++) 
     { 
      NameValuePair nvp = allParams.get(i); 
      if (i>0) { 
       params.append("&"); 
      } 
      params.append(nvp.getName() + "=" + OAuth.percentEncode(nvp.getValue())); 
     } 
     String signatureBaseStringTemplate = "%s&%s&%s"; 
     String signatureBaseString = String.format(signatureBaseStringTemplate, 
       OAuth.percentEncode(method), 
       OAuth.percentEncode(url), 
       OAuth.percentEncode(params.toString())); 
     String compositeKey = OAuth.percentEncode(oAuthConsumerSecret)+"&"; 
     if(withToken) compositeKey+=OAuth.percentEncode(oAuthTokenSecret); 
     oAuthSignature = Signature.calculateRFC2104HMAC(signatureBaseString, compositeKey); 

     return oAuthSignature; 
    } 

    public String generatedAuthorization(List<NameValuePair> allParams){ 
     authorization = "OAuth "; 
     Collections.sort(allParams, new NvpComparator()); 
     for(NameValuePair nvm : allParams){ 
      authorization+=nvm.getName()+"="+OAuth.percentEncode(nvm.getValue())+", "; 
     } 
     authorization=authorization.substring(0,authorization.length()-2); 
     return authorization; 
    } 

} 

açıklar:
1. getTwitterServerTime oAuthTimestamp yılında
Eğer sunucunun zaman ancak Heyecan sunucusunun zaman gerek yoktur. Her zaman belirli Twitter sunucusunda istekleri gönderiyorsanız, bu paramı kaydetmeyi optimize edebilirsiniz.

2. HeaderCreator.generatedSignature (...)
url - mantıksal twitter API
yöntemi url - GET veya POST.Her zaman "POST"
allParams kullanmanız gerekir - İmza oluşturmayı bildiğiniz parametreler ("param_name", "param_value");
withToken - oAuthTokenSecret'in doğru olduğunu biliyorsanız. Aksi halde yanlış.

3. HeaderCreator.generated Yetki Verme (...)
OluşturulanSignature (...) sonrasında bir OAuth başlık dizesi oluşturmak için bu yöntemi kullanın.
allParams - generateSignature (...) plus içinde kullandığınız parametrelerdir: nonce, imza, zaman damgası. Her zaman kullan:

allParams.add(new BasicNameValuePair("oauth_nonce", headerCreator.getoAuthNonce())); 
allParams.add(new BasicNameValuePair("oauth_signature", headerCreator.getoAuthSignature())); 
allParams.add(new BasicNameValuePair("oauth_timestamp", headerCreator.getoAuthTimestamp())); 


Artık kitaplığınızda UnpackedRequest.OAuth1Request doldurmak için kullanabilirsiniz.
Ayrıca SpringMVC'de kullanıcı kimliğini doğrulamak için bir örnek kütüphane:
İstekler - posta istekleri göndermek için.

public class Requests { 
    public static String sendPost(String url, String urlParameters, Map<String, String> prop) throws Exception { 
     URL obj = new URL(url); 
     HttpsURLConnection con = (HttpsURLConnection) obj.openConnection(); 

     con.setRequestMethod("POST"); 
     if(prop!=null) { 
      for (Map.Entry<String, String> entry : prop.entrySet()) { 
       con.setRequestProperty(entry.getKey(), entry.getValue()); 
      } 
     } 
     con.setDoOutput(true); 
     DataOutputStream wr = new DataOutputStream(con.getOutputStream()); 
     wr.writeBytes(urlParameters); 
     wr.flush(); 
     wr.close(); 
     int responseCode = con.getResponseCode(); 
     BufferedReader in; 
     if(responseCode==200) { 
      in = new BufferedReader(
        new InputStreamReader(con.getInputStream())); 
     }else{ 
      in = new BufferedReader(
        new InputStreamReader(con.getErrorStream())); 
     } 
     String inputLine; 
     StringBuffer response = new StringBuffer(); 
     while ((inputLine = in.readLine()) != null) { 
      response.append(inputLine); 
     } 
     in.close(); 

     return response.toString(); 
    } 
} 

twAuth (...) - Kumandanızda koydu. Bir kullanıcı sitenizde Twitter üzerinden kimlik doğrulaması yapmak istediğinde bunu uygulayın.

@RequestMapping(value = "/twauth", method = RequestMethod.GET) 
    @ResponseBody 
    public String twAuth(HttpServletResponse response) throws Exception{ 
     try { 
      String url = "https://api.twitter.com/oauth/request_token"; 

      List<NameValuePair> allParams = new ArrayList<NameValuePair>(); 
      allParams.add(new BasicNameValuePair("oauth_callback", "http://127.0.0.1:8080/twlogin")); 
      allParams.add(new BasicNameValuePair("oauth_consumer_key", "2YhNLyum1VY10UrWBMqBnatiT")); 
      allParams.add(new BasicNameValuePair("oauth_signature_method", "HMAC-SHA1")); 
      allParams.add(new BasicNameValuePair("oauth_version", "1.0")); 

      HeaderCreator headerCreator = new HeaderCreator("RUesRE56vVWzN9VFcfA0jCBz9VkvkAmidXj8d1h2tS5EZDipSL"); 
      headerCreator.generatedSignature(url,"POST",allParams,false); 
      allParams.add(new BasicNameValuePair("oauth_nonce", headerCreator.getoAuthNonce())); 
      allParams.add(new BasicNameValuePair("oauth_signature", headerCreator.getoAuthSignature())); 
      allParams.add(new BasicNameValuePair("oauth_timestamp", headerCreator.getoAuthTimestamp())); 

      Map<String, String> props = new HashMap<String, String>(); 
      props.put("Authorization", headerCreator.generatedAuthorization(allParams)); 
      String twitterResponse = Requests.sendPost(url,"",props); 
      Integer indOAuthToken = twitterResponse.indexOf("oauth_token"); 
      String oAuthToken = twitterResponse.substring(indOAuthToken, twitterResponse.indexOf("&",indOAuthToken)); 

      response.sendRedirect("https://api.twitter.com/oauth/authenticate?" + oAuthToken); 
     }catch (Exception ex){ 
      //TODO: Log 
      throw new Exception(); 
     } 
     return "main"; 
    } 

twLogin (...) - Kumandanızda koydu. Twitter'dan geri dönüş.

@RequestMapping(value = "/twlogin", method = RequestMethod.GET) 
    public String twLogin(@RequestParam("oauth_token") String oauthToken, 
          @RequestParam("oauth_verifier") String oauthVerifier, 
          Model model, HttpServletRequest request){ 
     try { 
      if(oauthToken==null || oauthToken.equals("") || 
        oauthVerifier==null || oauthVerifier.equals("")) 
       return "main"; 

      String url = "https://api.twitter.com/oauth/access_token"; 

      List<NameValuePair> allParams = new ArrayList<NameValuePair>(); 
      allParams.add(new BasicNameValuePair("oauth_consumer_key", "2YhNLyum1VY10UrWBMqBnatiT")); 
      allParams.add(new BasicNameValuePair("oauth_signature_method", "HMAC-SHA1")); 
      allParams.add(new BasicNameValuePair("oauth_token", oauthToken)); 
      allParams.add(new BasicNameValuePair("oauth_version", "1.0")); 
      NameValuePair oAuthVerifier = new BasicNameValuePair("oauth_verifier", oauthVerifier); 
      allParams.add(oAuthVerifier); 

      HeaderCreator headerCreator = new HeaderCreator("RUesRE56vVWzN9VFcfA0jCBz9VkvkAmidXj8d1h2tS5EZDipSL"); 
      headerCreator.generatedSignature(url,"POST",allParams,false); 
      allParams.add(new BasicNameValuePair("oauth_nonce", headerCreator.getoAuthNonce())); 
      allParams.add(new BasicNameValuePair("oauth_signature", headerCreator.getoAuthSignature())); 
      allParams.add(new BasicNameValuePair("oauth_timestamp", headerCreator.getoAuthTimestamp())); 
      allParams.remove(oAuthVerifier); 

      Map<String, String> props = new HashMap<String, String>(); 
      props.put("Authorization", headerCreator.generatedAuthorization(allParams)); 

      String twitterResponse = Requests.sendPost(url,"oauth_verifier="+oauthVerifier,props); 

      //Get user id 

      Integer startIndexTmp = twitterResponse.indexOf("user_id")+8; 
      Integer endIndexTmp = twitterResponse.indexOf("&",startIndexTmp); 
      if(endIndexTmp<=0) endIndexTmp = twitterResponse.length()-1; 
      Long userId = Long.parseLong(twitterResponse.substring(startIndexTmp, endIndexTmp)); 

      //Do what do you want... 

     }catch (Exception ex){ 
      //TODO: Log 
      throw new Exception(); 
     } 
    } 
+0

Böylesine ayrıntılı bir yanıtı paylaştığınız için teşekkür ederiz. –

İlgili konular