유니티용 애플 SDK 설치
Release Sign in with Apple Unity Plugin v1.4.2 · lupidan/apple-signin-unity
Changed Handles empty NSPersonNameComponents sent by Apple when not requesting a name, to be nil natively. Updated MacOSAppleAuthManager.bundle with the updated native code Removed Removes FixSe...
github.com
코드 작성
using System;
using System.Collections;
using System.Text;
using PlayFab;
using PlayFab.ClientModels;
using UnityEngine;
#if UNITY_IOS
using AppleAuth;
using AppleAuth.Native;
using AppleAuth.Enums;
using AppleAuth.Interfaces;
using AppleAuth.Extensions;
#endif
public class PlayfabManager : MonoBehaviour
{
#if UNITY_IOS
// 상수 및 필드
private const string AppleUserIdKey = "AppleUserId";
private IAppleAuthManager _appleAuthManager;
private bool _isAppleAuthInitialized = false;
// 이벤트 시스템 추가
public event Action<LoginResult> OnAppleLoginSuccess;
public event Action<string> OnAppleLoginFailed;
public event Action<bool> OnAppleLinkCompleted;
#endif
// 오류 처리 함수
private void DisplayPlayfabError(PlayFabError error)
{
string errorMessage = "PlayFab 오류: " + error.GenerateErrorReport();
Debug.LogError(errorMessage);
#if UNITY_IOS
OnAppleLoginFailed?.Invoke(errorMessage);
#endif
}
private void Awake()
{
#if UNITY_IOS
// 시작 시 Apple 인증 초기화
InitializeAppleAuth();
#endif
}
#if UNITY_IOS
// Apple 인증 초기화
private bool InitializeAppleAuth()
{
// 이미 초기화되었으면 중복 초기화 방지
if (_isAppleAuthInitialized)
return true;
// 플랫폼 지원 확인
if (!AppleAuthManager.IsCurrentPlatformSupported)
{
Debug.LogWarning("현재 플랫폼은 Apple 인증을 지원하지 않습니다.");
return false;
}
try
{
// 인증 관리자 초기화
var deserializer = new PayloadDeserializer();
_appleAuthManager = new AppleAuthManager(deserializer);
// 업데이트 코루틴 시작
StartCoroutine(AppleAuthUpdateCoroutine());
_isAppleAuthInitialized = true;
Debug.Log("Apple 인증 초기화 완료");
return true;
}
catch (Exception ex)
{
Debug.LogError($"Apple 인증 초기화 실패: {ex.Message}");
return false;
}
}
// Apple 인증 업데이트 코루틴
private IEnumerator AppleAuthUpdateCoroutine()
{
while (true)
{
// null 체크 추가
if (_appleAuthManager != null)
{
_appleAuthManager.Update();
}
yield return null;
}
}
// Apple 로그인 버튼 클릭 시 호출
public void OnClickAppleLogin()
{
Debug.Log("Apple 로그인 시도 중...");
// 초기화 확인
if (!_isAppleAuthInitialized && !InitializeAppleAuth())
{
string errorMessage = "Apple 인증을 초기화할 수 없습니다.";
Debug.LogError(errorMessage);
OnAppleLoginFailed?.Invoke(errorMessage);
return;
}
// 저장된 Apple ID 확인
string storedAppleUserId = PlayerPrefs.GetString(AppleUserIdKey, "");
bool hasExistingCredentials = !string.IsNullOrEmpty(storedAppleUserId);
StartCoroutine(AppleLoginCoroutine(hasExistingCredentials));
}
// Apple 로그인 코루틴
private IEnumerator AppleLoginCoroutine(bool useQuickLogin)
{
// 초기화 대기
while (_appleAuthManager == null)
{
yield return null;
}
try
{
if (useQuickLogin)
{
// 빠른 로그인 시도 (이전에 로그인한 적이 있는 경우)
Debug.Log("Apple 빠른 로그인 시도 중...");
var quickLoginArgs = new AppleAuthQuickLoginArgs();
_appleAuthManager.QuickLogin(
quickLoginArgs,
credential => {
var appleIdCredential = credential as IAppleIDCredential;
if (appleIdCredential != null)
{
// 사용자 ID 저장
PlayerPrefs.SetString(AppleUserIdKey, appleIdCredential.User);
PlayerPrefs.Save();
// PlayFab 로그인 처리
ProcessAppleLoginWithPlayFab(appleIdCredential.IdentityToken);
}
else
{
Debug.LogError("Apple 인증 정보가 올바르지 않습니다.");
OnAppleLoginFailed?.Invoke("인증 정보가 올바르지 않습니다.");
}
},
error => {
Debug.LogWarning($"Apple 빠른 로그인 실패: {error}, 전체 로그인 시도...");
StartCoroutine(PerformFullAppleSignIn());
});
}
else
{
// 전체 로그인 시도
yield return StartCoroutine(PerformFullAppleSignIn());
}
}
catch (Exception ex)
{
Debug.LogError($"Apple 로그인 중 오류 발생: {ex.Message}");
OnAppleLoginFailed?.Invoke(ex.Message);
}
}
// 전체 Apple 로그인 프로세스
private IEnumerator PerformFullAppleSignIn()
{
Debug.Log("Apple 전체 로그인 시도 중...");
bool signInCompleted = false;
Exception signInException = null;
// 이메일과 이름 정보 요청
var loginArgs = new AppleAuthLoginArgs(LoginOptions.IncludeEmail | LoginOptions.IncludeFullName);
_appleAuthManager.LoginWithAppleId(
loginArgs,
credential => {
var appleIdCredential = credential as IAppleIDCredential;
if (appleIdCredential != null)
{
// 사용자 ID 저장
PlayerPrefs.SetString(AppleUserIdKey, appleIdCredential.User);
PlayerPrefs.Save();
// 추가 정보 로깅 (디버그용)
if (!string.IsNullOrEmpty(appleIdCredential.Email))
Debug.Log($"Apple 이메일: {appleIdCredential.Email}");
if (appleIdCredential.FullName != null)
{
string fullName = "";
if (!string.IsNullOrEmpty(appleIdCredential.FullName.GivenName))
fullName += appleIdCredential.FullName.GivenName;
if (!string.IsNullOrEmpty(appleIdCredential.FullName.FamilyName))
{
if (!string.IsNullOrEmpty(fullName))
fullName += " ";
fullName += appleIdCredential.FullName.FamilyName;
}
if (!string.IsNullOrEmpty(fullName))
Debug.Log($"Apple 사용자 이름: {fullName}");
}
// PlayFab 로그인 처리
ProcessAppleLoginWithPlayFab(appleIdCredential.IdentityToken);
}
else
{
signInException = new Exception("Apple 인증 정보가 올바르지 않습니다.");
}
signInCompleted = true;
},
error => {
var authorizationErrorCode = error.GetAuthorizationErrorCode();
signInException = new Exception($"Apple 로그인 실패: {error} (코드: {authorizationErrorCode})");
signInCompleted = true;
});
// 로그인 완료 대기
while (!signInCompleted)
yield return null;
// 오류 발생 시 처리
if (signInException != null)
{
Debug.LogError(signInException.Message);
OnAppleLoginFailed?.Invoke(signInException.Message);
}
}
// PlayFab으로 Apple 로그인 처리
private void ProcessAppleLoginWithPlayFab(byte[] identityToken)
{
if (identityToken == null || identityToken.Length == 0)
{
Debug.LogError("Apple 인증 토큰이 비어있습니다.");
OnAppleLoginFailed?.Invoke("인증 토큰이 비어있습니다.");
return;
}
try
{
string tokenString = Encoding.UTF8.GetString(identityToken);
Debug.Log("PlayFab으로 Apple 로그인 시도 중...");
PlayFabClientAPI.LoginWithApple(
new LoginWithAppleRequest
{
CreateAccount = true,
IdentityToken = tokenString,
TitleId = PlayFabSettings.TitleId,
InfoRequestParameters = new GetPlayerCombinedInfoRequestParams
{
GetPlayerProfile = true,
GetUserAccountInfo = true
}
},
result => {
Debug.Log("PlayFab Apple 로그인 성공!");
OnLoginSuccess(result);
},
error => {
Debug.LogError($"PlayFab Apple 로그인 실패: {error.ErrorMessage}");
OnAppleLoginFailed?.Invoke(error.ErrorMessage);
});
}
catch (Exception ex)
{
Debug.LogError($"PlayFab 로그인 처리 중 오류 발생: {ex.Message}");
OnAppleLoginFailed?.Invoke(ex.Message);
}
}
// 계정 연결 기능
public void OnClickAppleLink(bool forceLink = false)
{
Debug.Log($"Apple 계정 연결 시도 중... (강제 연결: {forceLink})");
// 초기화 확인
if (!_isAppleAuthInitialized && !InitializeAppleAuth())
{
Debug.LogError("Apple 인증을 초기화할 수 없습니다.");
OnAppleLinkCompleted?.Invoke(false);
return;
}
try
{
var quickLoginArgs = new AppleAuthQuickLoginArgs();
_appleAuthManager.QuickLogin(
quickLoginArgs,
credential => {
var appleIdCredential = credential as IAppleIDCredential;
if (appleIdCredential != null)
{
LinkAppleAccountWithPlayFab(appleIdCredential.IdentityToken, forceLink);
}
else
{
Debug.LogError("Apple 인증 정보가 올바르지 않습니다.");
OnAppleLinkCompleted?.Invoke(false);
}
},
error => {
// 빠른 로그인 실패 시 전체 로그인 시도
var loginArgs = new AppleAuthLoginArgs(LoginOptions.IncludeEmail | LoginOptions.IncludeFullName);
_appleAuthManager.LoginWithAppleId(
loginArgs,
fullLoginCredential => {
var appleIdCredential = fullLoginCredential as IAppleIDCredential;
if (appleIdCredential != null)
{
LinkAppleAccountWithPlayFab(appleIdCredential.IdentityToken, forceLink);
}
else
{
Debug.LogError("Apple 인증 정보가 올바르지 않습니다.");
OnAppleLinkCompleted?.Invoke(false);
}
},
fullLoginError => {
Debug.LogError($"Apple 로그인 실패: {fullLoginError}");
OnAppleLinkCompleted?.Invoke(false);
});
});
}
catch (Exception ex)
{
Debug.LogError($"Apple 계정 연결 중 오류 발생: {ex.Message}");
OnAppleLinkCompleted?.Invoke(false);
}
}
// PlayFab으로 Apple 계정 연결
private void LinkAppleAccountWithPlayFab(byte[] identityToken, bool forceLink)
{
if (identityToken == null || identityToken.Length == 0)
{
Debug.LogError("Apple 인증 토큰이 비어있습니다.");
OnAppleLinkCompleted?.Invoke(false);
return;
}
try
{
string tokenString = Encoding.UTF8.GetString(identityToken);
PlayFabClientAPI.LinkApple(
new LinkAppleRequest
{
ForceLink = forceLink,
IdentityToken = tokenString
},
result => {
Debug.Log("Apple 계정 연결 성공!");
OnAppleLinkCompleted?.Invoke(true);
},
error => {
// 계정이 이미 다른 계정에 연결되어 있는 경우
if (error.Error == PlayFabErrorCode.AccountAlreadyLinked)
{
Debug.LogError("이 Apple 계정은 이미 다른 PlayFab 계정에 연결되어 있습니다.");
}
// 현재 계정이 이미 다른 Apple 계정에 연결되어 있는 경우
else if (error.Error == PlayFabErrorCode.LinkedAccountAlreadyClaimed)
{
Debug.LogError("현재 PlayFab 계정은 이미 다른 Apple 계정에 연결되어 있습니다.");
}
else
{
Debug.LogError($"Apple 계정 연결 실패: {error.ErrorMessage}");
}
OnAppleLinkCompleted?.Invoke(false);
});
}
catch (Exception ex)
{
Debug.LogError($"PlayFab 계정 연결 중 오류 발생: {ex.Message}");
OnAppleLinkCompleted?.Invoke(false);
}
}
#endif
// 로그인 성공 처리
public void OnLoginSuccess(LoginResult result)
{
Debug.Log("PlayFab 로그인 성공! PlayFabId: " + result.PlayFabId);
#if UNITY_IOS
// 이벤트 호출
OnAppleLoginSuccess?.Invoke(result);
#endif
// 로그인 성공 후 추가 처리
}
}
참고할만한 글
플레이팹 Playfab 게스트 로그인 Guest Login 간단 사용법
using PlayFab; using PlayFab.ClientModels; using PlayFab.Json; using PlayFab.ProfilesModels; using System; using System.Collections; using System.Collections.Generic; using UnityEngine; using Entity..
parksh3641.tistory.com
유니티 플레이팹 구글 로그인 Playfab Sign In with Google Login 간단 구현
구글 로그인 SDK 설치 https://github.com/playgameservices/play-games-plugin-for-unity/tree/master/current-build GitHub - playgameservices/play-games-plugin-for-unity: Google Play Games plugin for Unity Google Play Games plugin for Unity. Contribute t
parksh3641.tistory.com