Google Sign-In คือ SDK จาก Google ที่ implement การยืนยันตัวตนผู้ใช้ผ่านบัญชี Google ในแอปพลิเคชันมือถือและเว็บ เทคโนโลยีนี้ใช้โปรโตคอล OAuth 2.0 ซึ่งช่วยให้ได้รับโทเค็นการเข้าถึง Google API โดยไม่ต้องส่งรหัสผ่านไปยังแอปพลิเคชันของบุคคลที่สาม อุปกรณ์ Android มากกว่า 3 พันล้านเครื่องรองรับ Google Sign-In ทำให้เป็นวิธีการเข้าสู่ระบบที่พบได้บ่อยที่สุดในแอปมือถือ ตามข้อมูลจาก Google Identity Platform, 2025 การรวม SDK ช่วยลดเวลาการลงทะเบียนลง 60% และเพิ่ม Conversion ของผู้ใช้
ประเด็นสำคัญ
Google Sign-In คือบริการเข้าสู่ระบบครั้งเดียว (Single Sign-On) ที่ Google จัดเตรียมไว้สำหรับการยืนยันตัวตนผู้ใช้ในแอปพลิเคชันของบุคคลที่สาม SDK ช่วยให้นักพัฒนาสามารถรวมการเข้าสู่ระบบผ่านบัญชี Google โดยไม่ต้องสร้างระบบลงทะเบียนของตนเอง เทคโนโลยีนี้ใช้โปรโตคอล OAuth 2.0 และ OpenID Connect ซึ่งให้ข้อมูลประจำตัวผู้ใช้: ชื่อ อีเมล อวาตาร์ และตัวระบุที่ไม่ซ้ำกัน
แตกต่างจากการยืนยันตัวตนแบบเดิมด้วยอีเมลและรหัสผ่าน Google Sign-In ช่วยลดความจำเป็นในการจำรหัสผ่านและผ่านขั้นตอนการลงทะเบียน ผู้ใช้เลือกบัญชี Google บนอุปกรณ์ ยืนยันสิทธิ์ และแอปจะได้รับโทเค็นการเข้าถึง ตามข้อมูลจาก Google Identity Platform (2025) แอปที่มี Google Sign-In แสดงการลงทะเบียนที่สำเร็จมากกว่า 52% เมื่อเทียบกับฟอร์มอีเมล/รหัสผ่าน
Google Sign-In รองรับสามสถานการณ์การใช้งาน: การยืนยันตัวตนผู้ใช้ (การรับ ID Token), การอนุญาตให้เข้าถึง Google API (การรับ Access Token) และการยืนยันตัวตนแบบไร้รอยต่อ (Silent Sign-In) สำหรับผู้ใช้ที่ได้รับอนุญาตแล้ว แต่ละสถานการณ์ต้องใช้ชุดขอบเขต (scopes) ที่แตกต่างกันและคืนค่าโทเค็นประเภทต่าง ๆ
OAuth 2.0 คือโปรโตคอลการอนุญาตที่ช่วยให้แอปสามารถเข้าถึงทรัพยากรของผู้ใช้ได้อย่างจำกัดโดยไม่เปิดเผยข้อมูลประจำตัวของพวกเขา ในบริบทของ Google Sign-In โปรโตคอลทำงานดังนี้: แอปขออนุญาตจากผู้ใช้ผ่าน Google รับรหัสอนุญาตชั่วคราว แลกเปลี่ยนเป็นโทเค็นการเข้าถึง และใช้โทเค็นเหล่านั้นเพื่อเรียก Google API
ความแตกต่างหลักของ OAuth 2.0 จากโปรโตคอลก่อนหน้านี้คือการแยกบทบาทระหว่างเจ้าของทรัพยากร (ผู้ใช้), ไคลเอนต์ (แอป), เซิร์ฟเวอร์อนุญาต (Google) และเซิร์ฟเวอร์ทรัพยากร (Google API) แอปไม่เคยได้รับรหัสผ่านของผู้ใช้ — มีเพียงโทเค็นที่สามารถเพิกถอนได้ Google Identity Platform ใช้ข้อกำหนด OpenID Connect บน OAuth 2.0 เพิ่ม ID Token ที่เป็นมาตรฐานในรูปแบบ JWT
// ตัวอย่างการรับ ID Token ผ่าน Credential Manager
val googleIdOption = GoogleIdCredentialOption.Builder()
.setServerClientId(serverClientId)
.build()
val credentialManager = CredentialManager.create(this)
val request = GetCredentialRequest.Builder()
.addCredentialOption(googleIdOption)
.build()
credentialManager.getCredential(request)
.addOnSuccessListener { result ->
val credential = result.credential as GoogleIdCredential
Log.d("SignIn", credential.idToken)
}ID Token (JWT) ประกอบด้วยสามส่วน: ส่วนหัวที่มีอัลกอริทึมลายเซ็น, Payload ที่มีข้อมูลผู้ใช้ (sub, email, name, picture) และลายเซ็นสำหรับการตรวจสอบ ส่วนเซิร์ฟเวอร์ของแอปตรวจสอบลายเซ็น ID Token โดยใช้คีย์สาธารณะของ Google และแยกตัวระบุผู้ใช้ วิธีการนี้รับประกันว่าแม้ว่าแอปไคลเอนต์จะถูกบุกรุก ผู้โจมตีก็ไม่สามารถปลอมแปลงโทเค็นได้หากไม่สามารถเข้าถึงคีย์ส่วนตัวของ Google
Credential Manager คือ Android API ที่ทันสมัยซึ่งเปิดตัวในปี 2023 ที่รวมวิธีการยืนยันตัวตนทั้งหมด (Google Sign-In, การเข้าสู่ระบบด้วยรหัสผ่าน, Passkeys) เป็นอินเทอร์เฟซผู้ใช้เดียว แตกต่างจาก GoogleSignInClient แบบเก่า Credential Manager ไม่จำเป็นต้องใช้ WebView ในการเข้าสู่ระบบ — มันใช้ Bottom Sheet ดั้งเดิม ซึ่งช่วยเร่งการยืนยันตัวตนและปรับปรุงประสบการณ์ผู้ใช้
ข้อได้เปรียบหลักของ Credential Manager คือ UX ที่เป็นหนึ่งเดียวสำหรับข้อมูลประจำตัวทุกประเภท ผู้ใช้เห็นกล่องโต้ตอบเดียวที่สามารถเลือก: เข้าสู่ระบบด้วย Google, ใช้ Passkey หรือป้อนรหัสผ่าน นักพัฒนาไม่จำเป็นต้องจัดการโฟลว์การยืนยันตัวตนที่แตกต่างกัน — Credential Manager จัดการปฏิสัมพันธ์กับ Google Sign-In, Smart Lock และ Passkeys โดยอัตโนมัติ Google แนะนำ Credential Manager เป็นวิธีหลักในการรวม Google Sign-In สำหรับ Android 14+
| พารามิเตอร์ | GoogleSignInClient (แบบเก่า) | Credential Manager |
|---|---|---|
| API ขั้นต่ำ | Android 4.4 (API 19) | Android 4.4 (API 19) |
| อินเทอร์เฟซ | WebView / BottomSheet | BottomSheet ดั้งเดิม |
| รองรับ Passkey | ไม่ | ใช่ |
| ขนาด SDK | ~500 KB | ~150 KB |
| สถานะ | เลิกใช้งาน (2024) | แนะนำโดย Google |
การย้าย จาก GoogleSignInClient ไปยัง Credential Manager ต้องเปลี่ยนตรรกะฝั่งไคลเอนต์: แทนที่จะใช้ GoogleSignInOptions ให้ใช้ GoogleIdCredentialOption และแทนที่จะใช้ GoogleSignIn.getSignedInAccountFromIntent ให้จัดการผลลัพธ์ผ่าน GetCredentialResponse ส่วนฝั่งเซิร์ฟเวอร์ไม่ต้องการการเปลี่ยนแปลงเนื่องจาก ID Token ยังคงรูปแบบ JWT เดิม ตามข้อมูลจาก Google I/O 2024 ประมาณ 40% ของแอปบน Google Play ได้ย้ายไปใช้ Credential Manager แล้ว
การรวม Google Sign-In ในแอป Android เริ่มต้นด้วยการกำหนดค่าโปรเจกต์ใน Google Cloud Console ขั้นตอนแรกคือการสร้าง OAuth 2.0 Client ID สำหรับ Android: ระบุชื่อแพ็คเกจของแอปและลายนิ้วมือใบรับรอง SHA-1 Google ใช้ข้อมูลนี้เพื่อตรวจสอบว่าคำขอการยืนยันตัวตนมาจากแอปของคุณ ไม่ใช่จากไคลเอนต์ปลอม
หลังจากสร้างไคลเอนต์ใน Google Cloud Console นักพัฒนาเพิ่ม dependency Credential Manager ใน build.gradle และกำหนดค่า GoogleIdCredentialOption ด้วย serverClientId สำคัญ: serverClientId คือ Client ID ของเว็บแอปพลิเคชันจากโปรเจกต์ Google Cloud เดียวกัน ซึ่งฝั่งเซิร์ฟเวอร์ใช้ตรวจสอบ ID Token แอปไคลเอนต์ไม่ตรวจสอบโทเค็น — มันเพียงรับและส่งต่อไปยังเซิร์ฟเวอร์
// build.gradle (app) dependencies
implementation("androidx.credentials:credentials:1.5.0")
implementation("androidx.credentials:credentials-play-services-auth:1.5.0")
implementation("com.google.android.libraries.identity.googleid:googleid:1.1.0")
// ขอ Google Sign-In ผ่าน Credential Manager
suspend fun requestGoogleSignIn(context: Context): String? {
val credentialManager = CredentialManager.create(context)
val googleIdOption = GoogleIdCredentialOption.Builder()
.setServerClientId(BuildConfig.SERVER_CLIENT_ID)
.setAutoSelectEnabled(true)
.build()
val result = credentialManager.getCredential(
context as Activity,
GetCredentialRequest.Builder()
.addCredentialOption(googleIdOption)
.build()
)
return (result.credential as GoogleIdCredential).idToken
}หลังจากรับ ID Token บนไคลเอนต์ แอปจะส่งไปยังเซิร์ฟเวอร์เพื่อทำการตรวจสอบ เซิร์ฟเวอร์ตรวจสอบลายเซ็น JWT โดยใช้คีย์สาธารณะของ Google (มีให้ที่ https://www.googleapis.com/oauth2/v3/certs), เวลาหมดอายุของโทเค็น (exp) และค่าของฟิลด์ aud — ต้องตรงกับ serverClientId หลังจากการตรวจสอบ เซิร์ฟเวอร์สร้างเซสชันของตัวเอง เช่น ออก JWT ภายในหรือ Session Token
การรวม Google Sign-In บน iOS ทำผ่าน SDK GoogleSignIn-iOS ซึ่งมีให้ผ่าน CocoaPods หรือ Swift Package Manager กระบวนการตั้งค่ารวมถึงการสร้าง Client ID สำหรับ iOS ใน Google Cloud Console (ระบุ Bundle Identifier), การเพิ่ม URL Scheme สำหรับ callback และการกำหนดค่า AppDelegate เพื่อจัดการ URL ที่ Google ส่งกลับหลังจากการยืนยันตัวตน
ความแตกต่างที่สำคัญของเวอร์ชัน iOS ของ Google Sign-In จาก Android คือความจำเป็นในการกำหนดค่า URL Scheme และ Info.plist GoogleSDK ใช้ Universal Links สำหรับ callback แต่สำหรับ Fallback ต้องใช้ URL Scheme ในรูปแบบ `com.googleusercontent.apps.[CLIENT_ID]` นอกจากนี้ยังต้องกำหนดค่า Keychain Sharing เพื่อบันทึก refresh token ระหว่างการเปิดใช้แอป ตามเอกสาร Google Identity, iOS SDK รองรับ iOS 15 ขึ้นไป
// การตั้งค่า Google Sign-In บน iOS
import GoogleSignIn
class SignInManager: ObservableObject {
func signIn(presenting viewController: UIViewController) {
GIDSignIn.sharedInstance.signIn(
withPresenting: viewController
) { signInResult, error in
guard let result = signInResult else {
print("Sign in failed: \(error)")
return
}
let idToken = result.user.idToken.tokenString
// ส่ง ID Token ไปยังเซิร์ฟเวอร์
sendTokenToBackend(idToken)
}
}
}บน iOS Google Sign-In รองรับ Silent Sign-In สำหรับผู้ใช้ที่เคยอนุญาตไว้ก่อนหน้านี้ เมธอด restorePreviousSignIn จะกู้คืนเซสชันโดยอัตโนมัติหากบันทึก refresh token ไว้ใน Keychain ซึ่งสำคัญโดยเฉพาะสำหรับแอปที่ผู้ใช้ไม่ควรต้องเข้าสู่ระบบใหม่ทุกครั้งที่เปิดใช้ ตามข้อมูลของ Google Silent Sign-In สำเร็จใน 85% ของกรณีบนอุปกรณ์ที่มีเซสชัน Google ที่ใช้งานอยู่
ความปลอดภัย ของ Google Sign-In สร้างขึ้นบนสามระดับ: การตรวจสอบไคลเอนต์ (ลายเซ็น SHA-1 ของแอป), การเข้ารหัสการขนส่ง (HTTPS/TLS) และลายเซ็น JWT เข้ารหัส ID Token ที่ได้รับจาก Google ลงนามโดยใช้อัลกอริทึม RS256 (RSA กับ SHA-256) ส่วนเซิร์ฟเวอร์ของแอปต้องตรวจสอบลายเซ็นโทเค็น วันหมดอายุ และผู้ออก (iss) — accounts.google.com เท่านั้น
Access Token คือโทเค็นชั่วคราว (มีอายุ 1 ชั่วโมง) ที่ให้การเข้าถึง Google API (Google Drive, Google Calendar, YouTube ฯลฯ) แตกต่างจาก ID Token Access Token ไม่มีข้อมูลผู้ใช้ — มันเป็นสตริงทึบแสงที่เซิร์ฟเวอร์ Google API ใช้สำหรับการอนุญาตคำขอ Refresh Token คือโทเค็นที่มีอายุยาวนานซึ่งช่วยให้ได้รับ Access Token ใหม่โดยไม่ต้องให้ผู้ใช้เข้าสู่ระบบอีกครั้ง Refresh Token จะออกให้เฉพาะในการเข้าสู่ระบบครั้งแรกเท่านั้นและผู้ใช้สามารถเพิกถอนได้ในการตั้งค่าบัญชี Google
// ตัวอย่างการประมวลผล ID Token บนเซิร์ฟเวอร์ (รหัสเทียม)
fun verifyGoogleToken(idToken: String): User? {
val verifier = GoogleIdTokenVerifier.Builder(
NetHttpTransport(), GsonFactory.getDefaultInstance()
).setAudience(listOf(CLIENT_ID))
.build()
val token = verifier.verify(idToken) ?: return null
val payload = token.payload
return User(
id = payload.subject,
email = payload.email,
name = payload.get("name") as String
)
}คำแนะนำด้านความปลอดภัย: อย่าส่ง ID Token ผ่านช่องทางที่ไม่ปลอดภัย ใช้ HTTPS สำหรับคำขอทั้งหมดไปยังเซิร์ฟเวอร์ ตรวจสอบวันหมดอายุของโทเค็น (ฟิลด์ exp) และผู้ออก (iss) บนไคลเอนต์ อย่าเก็บโทเค็นใน SharedPreferences โดยไม่เข้ารหัส — ใช้ EncryptedSharedPreferences หรือ Android Keystore Google Sign-In ไม่ได้ออกแบบมาสำหรับการยืนยันตัวตนเซิร์ฟเวอร์ถึงเซิร์ฟเวอร์ — สำหรับกรณีนั้นให้ใช้ Service Accounts
ตัวอย่างที่สมบูรณ์ของการรวม Google Sign-In ในแอป Android โดยใช้ Credential Manager และ ViewModel แอปแสดงปุ่มเข้าสู่ระบบ หลังจากยืนยันตัวตนจะส่ง ID Token ไปยังเซิร์ฟเวอร์และแสดงข้อมูลผู้ใช้ โค้ดใช้ Coroutine สำหรับการทำงานแบบอะซิงโครนัสกับ Credential Manager
class SignInViewModel: ViewModel() {
private val cm = CredentialManager.create(getApplication())
private val googleOption = GoogleIdCredentialOption.Builder()
.setServerClientId(BuildConfig.SERVER_CLIENT_ID)
.build()
suspend fun signIn(): SignInResult {
return try {
val response = cm.getCredential(
GetCredentialRequest.Builder()
.addCredentialOption(googleOption)
.build()
)
val credential = response.credential as GoogleIdCredential
SignInResult.Success(credential.idToken)
} catch (e: GetCredentialCancellationException) {
SignInResult.Cancelled
}
}
}
sealed class SignInResult {
data class Success(val idToken: String) : SignInResult()
data class Error(val message: String) : SignInResult()
data class Cancelled : SignInResult()
}หลังจากการยืนยันตัวตนสำเร็จ แอปควรส่ง ID Token ไปยังเซิร์ฟเวอร์เพื่อตรวจสอบและสร้างเซสชัน แนะนำให้ใช้ HTTPS และส่งโทเค็นในเนื้อหาของคำขอ POST เซิร์ฟเวอร์จะส่งคืนโทเค็นเซสชันของตัวเอง ซึ่งไคลเอนต์เก็บไว้ใน EncryptedSharedPreferences ในการขอแต่ละครั้งต่อไปยังเซิร์ฟเวอร์ จะใช้โทเค็นภายใน ไม่ใช่ ID Token ของ Google
ข้อผิดพลาดทั่วไปแรกคือความไม่ตรงกันของใบรับรอง SHA-1 Google Cloud Console ผูก OAuth 2.0 Client ID กับลายนิ้วมือใบรับรอง SHA-1 หากแอปถูกสร้างด้วยคีย์ดีบักแต่ Client ID ถูกสร้างสำหรับคีย์รีลีส Google Sign-In จะส่งคืนข้อผิดพลาด 12501 (SIGN_IN_FAILED) วิธีแก้ไข: เพิ่มลายนิ้วมือ SHA-1 ทั้งสอง (ดีบักและรีลีส) ใน Google Cloud Console หรือใช้ Client ID หนึ่งสำหรับการพัฒนาและอีกอันแยกสำหรับโปรดักชัน
ปัญหาที่พบบ่อยที่สองคือ serverClientId ไม่ถูกต้อง นักพัฒนามักใช้ Android Client ID แทน Client ID ของเว็บแอปพลิเคชันในพารามิเตอร์ serverClientId ของ Credential Manager Google ต้องการ Client ID ของเว็บอย่างแม่นยำเพื่อสร้าง ID Token สำหรับการตรวจสอบเซิร์ฟเวอร์ Android Client ID ใช้สำหรับระบุแอประหว่างการยืนยันตัวตนเท่านั้น ตรวจสอบให้แน่ใจว่า serverClientId ตรงกับเว็บแอปพลิเคชันใน Google Cloud Console
ข้อผิดพลาดที่สามคือการละเลยการจัดการการยกเลิก ผู้ใช้อาจปิดกล่องโต้ตอบ Google Sign-In โดยไม่เสร็จสิ้นการยืนยันตัวตน Credential Manager จะโยน GetCredentialCancellationException ซึ่งต้องจัดการแยกจากข้อผิดพลาดอื่น ๆ นักพัฒนาหลายคนจัดการข้อยกเว้นทั้งหมดเป็นข้อผิดพลาด แสดงข้อความ “เข้าสู่ระบบล้มเหลว” ให้ผู้ใช้เห็น ในขณะที่ผู้ใช้เพียงแค่ยกเลิกการดำเนินการ การจัดการที่ถูกต้อง: เมื่อถูกยกเลิก — ไม่ต้องแสดงอะไรเลย เพียงกลับไปยังสถานะเริ่มต้น
คำถามที่พบบ่อย
แนะนำให้ใช้ Credential Manager (AndroidX Credentials) สำหรับ Android และ GIDSignin SDK ผ่าน Swift Package Manager สำหรับ iOS Credential Manager เป็น API ที่ทันสมัยซึ่ง Google รองรับ รวม Google Sign-In, Passkeys และการเข้าสู่ระบบด้วยรหัสผ่านในอินเทอร์เฟซเดียว GoogleSignInClient ที่เลิกใช้งานแล้ว (com.google.android.gms:auth) ไม่แนะนำให้ใช้อีกต่อไป
ID Token คือ JWT ที่มีข้อมูลผู้ใช้ (ชื่อ อีเมล ID ที่ไม่ซ้ำกัน) ใช้สำหรับการยืนยันตัวตนบนฝั่งเซิร์ฟเวอร์ของแอป Access Token คือสตริงทึบแสงสำหรับเข้าถึง Google API (Google Drive, Calendar) ID Token มีอายุ 1 ชั่วโมง Access Token ก็มีอายุ 1 ชั่วโมงเช่นกัน แต่สามารถต่ออายุได้ผ่าน Refresh Token
ในทางเทคนิคสามารถทำได้ แต่ไม่ปลอดภัย หากคุณตรวจสอบ ID Token เฉพาะบนไคลเอนต์ ผู้โจมตีสามารถดีคอมไพล์แอปและแยกตรรกะการตรวจสอบได้ การตรวจสอบฝั่งเซิร์ฟเวอร์ด้วยคีย์สาธารณะของ Google รับประกันว่าโทเค็นนั้นออกโดย Google จริงและไม่ได้ถูกปลอมแปลง สำหรับแอปที่ไม่มีเซิร์ฟเวอร์ ให้ใช้ Firebase Authentication
ข้อผิดพลาด 12501 (SIGN_IN_FAILED) เกิดขึ้นเมื่อใบรับรอง SHA-1 ของแอปไม่ตรงกับที่ระบุใน Google Cloud Console วิธีแก้ไข: เพิ่ม SHA-1 จากใบรับรองดีบัก (จาก Android Studio) และใบรับรองรีลีสในคอนโซล นอกจากนี้ตรวจสอบว่าชื่อแพ็คเกจในคอนโซลตรงกับ build.gradle หลังจากการเปลี่ยนแปลงอาจใช้เวลาถึง 24 ชั่วโมงในการเผยแพร่
ไม่ Google Sign-In ต้องการการเชื่อมต่ออินเทอร์เน็ตเพื่อสื่อสารกับเซิร์ฟเวอร์ของ Google หากอุปกรณ์ออฟไลน์ ให้ใช้กลไกแคชเซสชัน: หลังจากเข้าสู่ระบบสำเร็จ ให้บันทึกโทเค็นใน EncryptedSharedPreferences และตรวจสอบความถูกต้องในการเปิดใช้ครั้งถัดไป เมื่อไม่มีเครือข่าย ให้แสดงข้อมูลที่บันทึกไว้และแนะนำให้เข้าสู่ระบบในภายหลัง
สรุป
เราจะพัฒนาแอปพลิเคชันบนมือถือแบบครบวงจร
IT Sectr สร้างแอปพลิเคชัน iOS และ Android สำหรับสตาร์ทอัพและธุรกิจตั้งแต่ปี 2017 เราจะให้คำแนะนำและเสนอวิธีแก้ปัญหาที่ดีที่สุดแก่คุณ