2014-09-14 4 views
9

जब एंड्रॉयड में AccountManager में एक कस्टम खाता प्रकार को लागू करने मैं प्रवाह में हस्ताक्षर के लिए निम्नलिखित समस्या है:ब्राउज़र इरादे और सही गतिविधि (करीब खोला टैब) पर लौटने

एक OAuth प्रदाता के माध्यम से होना चाहिए में साइन इन करें। इसलिए मैंने SignInActivity बनाया है जो WebView लॉन्च करता है और ओएथ प्रवाह शुरू करता है। यह ठीक काम करता है, जब कॉलबैक my-custom-scheme://callback पर प्राप्त होता है WebView इसे पहचानता है, code क्वेरीस्ट्रिंग पैरामीटर प्राप्त करता है और प्रवाह को पूरा करता है। WebView का उपयोग करने के साथ नुकसान यह है कि भले ही उपयोगकर्ता के पास ब्राउज़र में सक्रिय सत्र हो, फिर भी इस सत्र का उपयोग WebView में नहीं किया जाता है, इसलिए उपयोगकर्ता को WebView में फिर से लॉगिन करना होगा।

इस का समाधान करने के लिए, मैं AndroidManifest.xml में एक intent-filter का उपयोग कर का उपयोग करने जा, इस तरह की कोशिश की:

<intent-filter> 
    <action android:name="android.intent.action.VIEW" /> 
    <category android:name="android.intent.category.DEFAULT" /> 
    <category android:name="android.intent.category.BROWSABLE" /> 
    <data android:scheme="my-custom-scheme" android:path="callback"/> 
</intent-filter> 

के बजाय SignInActivity में एक WebView खोलने, मैं तो एक ब्राउज़र आशय का शुभारंभ और ब्राउज़र को हिट करने के लिए प्रतीक्षा करें my-custom-scheme://callback

if (intent != null && intent.getData() != null && getString("my-custom-scheme").equals(intent.getData().getScheme())) { 
    String code = getIntent().getData().getQueryParameter("code"); 
    // complete oauth flow 
} 

यह काम करता है:

Intent browserIntent = new Intent(Intent.ACTION_VIEW, "http://oauth2provider/authorize"); 
startActivity(browserIntent); 
finish(); 

मेरी SignInActivity में मैं कॉलबैक को संभालने के लिए निम्नलिखित कोड है। लेकिन, समस्या (अंत में!) करने के लिए:

  1. उपयोगकर्ता प्रवेश नहीं है, तो ब्राउज़र आशय OAuth प्रदाता के लिए साइन इन पृष्ठ प्रदर्शित करेगा। उपयोगकर्ता ने साइन इन करने के बाद, क्रोम मेरी-कस्टम-स्कीम पर रीडायरेक्ट करेगा: // कॉलबैक और SignInActivity इरादे को संभालने के लिए लॉन्च होगा। चूंकि यह गतिविधि अदृश्य है, ब्राउज़र साइन इन पेज पर खुला रहेगा, और उपयोगकर्ता को ऐसा कुछ भी नहीं लगेगा जैसा दिखता है। ब्राउज़र कभी बंद नहीं होता है।
  2. यदि उपयोगकर्ता पहले से ही साइन इन है, तो oauth प्रदाता सीधे मेरी-कस्टम-योजना: // कॉलबैक पर रीडायरेक्ट करेगा। इस मामले में, ब्राउज़र टैब स्वचालित रूप से बंद हो गया है लेकिन ब्राउज़र स्वयं ही खुला रहता है (बिना टैब दिखाई दे रहा है)।

तो मेरा सवाल यह है: क्या मेरे कस्टम-स्कीम: // कॉलबैक पर रीडायरेक्ट होने के बाद ब्राउज़र अलग-अलग व्यवहार करने के लिए वैसे भी है? आदर्श रूप से, मैं इसे कॉलबैक पर रीडायरेक्ट करने के बाद बस बंद करना चाहता हूं, और गतिविधि स्टैक में पिछली गतिविधि पर लौटने के लिए (यानी उस गतिविधि के लिए जिसने शुरुआत से SignInActivity शुरू किया था)।

उत्तर

4

मैंने एक ही समस्या को ठीक करने के लिए अगले दृष्टिकोण का उपयोग किया।

मान लें कि हमारे पास MainActivitySign In बटन के साथ है। इसके बजाय ब्राउज़र को सीधे उस बटन पर क्लिक करने के लिए मैं startActivityForResult विधि का उपयोग कर शुरू कर रहा हूं। इसके लिए मैं उपयोग कर रहा हूं मैं लॉगिन प्रवाह के परिणाम संभाल सकता हूं।

startActivityForResult(new Intent(this, SignInActivity.class), requestCode);

SignInActivity लिए जिम्मेदार है:

  • प्रवेश पृष्ठ के साथ खुला ब्राउज़र
  • पकड़ का उपयोग कर custom-scheme://callback
  • खत्म लॉग इन प्रवाह को अनुप्रेषित टोकन पुनः निर्देशित यूआरएल से
  • वापसी परिणाम वापस प्राप्त MainActivity

तो, अपने onCreate विधि लगता है:

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.login); 

    if (intent != null && intent.getData() != null && "custom-scheme".equals(intent.getData().getScheme())) { 
     String code = getIntent().getData().getQueryParameter("code"); 
     // complete oauth flow 
    } else { 
     Intent browserIntent = new Intent(Intent.ACTION_VIEW, "http://oauth2provider/authorize") 
      .setFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_NO_HISTORY | Intent.FLAG_FROM_BACKGROUND); 
     startActivity(browserIntent); 
     finish(); 
    } 
} 

ब्राउज़र अभिप्राय के संबंध में सेट झंडे स्वीकार।

इस तरह अगर SignInActivityMainActivity से खोला जाता है यह सिर्फ ब्राउज़र में प्रवेश पृष्ठ को खोलता है और अगर यह पकड़ने खुले का यूआरएल अनुप्रेषित यह लॉग इन प्रवाह उचित अनुरोध भेजने पूरा करता है।

के बाद आप पूरी लॉगिन अपने कॉलबैक विधि में कुछ समाप्ति बिंदु को कोड भेजने के प्रवाह आप निम्न करना चाहिए:

setResult(Activity.RESULT_OK); 
this.finish(); 

स्वाभाविक रूप से, आपको लगता है कि अंत बिंदु से ACCESS_TOKEN प्राप्त करते हैं। आप सफलतापूर्वक कॉलबैक में कहीं भी इसे स्टोर कर सकते हैं या उसे वहां संभालने के लिए MainActivity पर वापस कर सकते हैं।

SignInActivity के लिए लेआउट के रूप में आप पृष्ठ के केंद्र में केवल ProgressBar का उपयोग कर सकते हैं। SignInActivity के बाद लॉगिन प्रवाह पूर्ण होने के दौरान यह दिखाई देगा, यूआरएल (custom-scheme://callback) पकड़ा गया है।

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
> 

    <ProgressBar 
     android:layout_width="48dp" 
     android:layout_height="48dp" 
     android:layout_centerVertical="true" 
     android:layout_centerHorizontal="true" 
    /> 
</RelativeLayout> 

यहाँ AndroidManifest.xml

<activity android:name=".SignInActivity" 
      android:launchMode="singleTask" 
      android:noHistory="true" 
    > 
    <intent-filter> 
     <action android:name="android.intent.action.VIEW" /> 
     <category android:name="android.intent.category.DEFAULT"/> 
     <category android:name="android.intent.category.BROWSABLE"/> 
     <data android:scheme="custom-scheme" android:host="callback"/> 
    </intent-filter> 
</activity> 
में SignInActivity की घोषणा है
संबंधित मुद्दे