개요
Tencent 게임의 결제는 Midas로 통합되어 있습니다. Midas는 Tencent에서 공식적으로 제공하는 모바일 클라이언트 결제 SDK로, QQ화폐, QQ카드, 차이푸통(财付通), 은행카드, 위챗 패이, 휴대폰 충전 카드, 전화요금 등의 결제 채널입니다. 네이티브 android 및 iap(애플 공식 버전) 결제 SDK, 그리고 일련의 지불 서비스와 함께 마케팅 활동을 포함한 지원을 제공합니다. 여기서는 간략하게 소개할 것이며, 상세 정보는 Midas wiki를 참조하시기 바랍니다.
액세스 내비게이션
1 사전 요구 사항
1) MSDK 로그인 액세스 완료
결제 시에 pf, pfkey, openid, pay_token(모바일QQ 로그인 시 필요), accessToken(위챗 로그인 시 필요)과 같은 일련의 토큰 정보를 입력해야 하며, 해당 정보는 모두 로그인 성공 후에 획득됩니다. 로그인 가능한 및
토큰 정보 획득 방법을 참조하십시오. 그 외에도, 귀하께서는 offerid, offerid를 입력하고 http://midas.qq.com에서 신청해야 합니다.
2) Midasu의 다른 요구 사항 수행
상세 정보는 Midas 준비 작업 액세스를 참조하십시오.
2 게임 결제 정보 설정
Midas의 웹사이트에서 게임 화폐 모드, 아이템 직접 구매 방식을 등록 및 설정할 필요가 있습니다. 상세 정보는 iOS 결제 설정 상세 정보를 참조해 주십시오.
3 Midas SDK 액세스와 통합 및 테스트
IOS는 MidasIAPSDK.framework 패키지를 설치하고 SDK 요청 등을 설정해야 합니다.
1) MidasSDK 리소스 가져오기
Midas 공식 웹사이트에서 MidasIOS의 sdk를 다운로드하십시오.
MidasSDK 안에 있는 MidasIAPSDK.framework를 설치합니다.
a) MidasIAPSDK.framework 패키지를 설치합니다.
(./res/midas_ios_import_framework1.png) (./res/midas_ios_import_framework2.png)
b) MidasIAPSDK.framework를 선택해 설치합니다.
(./res/midas_ios_import_framework3.png)
설치 후에 다음과 같이 표시됩니다.
(./res/midas_ios_import_framework4.png)
2) 리소스 bundle 설치의 경우, Finder 내에서 MidasIAPSDK.bundle 파일을 찾으십시오.
(./res/midas_ios_import_bundle1.png)
정확한 bundle 내 리소스를 호출할 수 있도록, 리소스 bundle을 설치한 후에, 프로젝트의 설정 내에 MidasIAPSDK.bundle이 표시되어 있는 것을 확인하면 됩니다. 없을 경우, SDK가 bundle 내 리소스를 획득하지 못할 수 있고, 인터페이스 오류가 유발됩니다. 설치에 성공한 후의 인터페이스는 아래 그림과 같습니다.
(./res/midas_ios_import_bundle2.png)
3) 프로젝트 설정
Midas SDK가 종속되는 시스템 framework와 라이브러리는 libz.dylib, Foundation.framework, MobileCoreService.framework, SystemConfiguration.framework, StoreKit.framework 등입니다. Build Phase 내에서 이 종속 변수들을 타겟 프로젝트 안에 추가합니다. 이 SDK는 주로 StoreKit 안의 In App Purchase 기능을 채택하고 있으므로, 최정적으로 위 그림의 Capabilities 내에서 In-App Purchase 기능을 기동합니다.
(./res/midas_ios_config_purchase.png)
IOS SDK액세스를 참조하십시오.
2 MidasSDK 인터페이스 호출
1) 상위 윈도우 핸들 설정
a) 기능 설명
상위 윈도우 핸들을 설정하며, MidasSDK에 쇼핑센터 페이지를 표시하거나 H5 페이지를 풀업합니다.
b) 인터페이스 선언
- (void)setParentViewController:(UIViewController *)parent
c) 파라미터 설명
파라미터 명칭 | 파라미터 유형 | 설명 |
---|---|---|
parent | UIViewController * | 상위 윈도우 핸들 |
d) 반환값
없음
e) 예시 코드
[[IAPPayHelper getIntanceIapHelp] setParentViewController:UIViewController];
2) 결제 콜백 Delegate의 실행 및 설정
a) 기능 설명
IAP 결제 콜백 통지 대상을 설정하고 결제 결과 콜백을 획득합니다.
b) 인터페이스 선언
@property (nonatomic, assign) id<IAPPayDelegate> Delegate
c) 파라미터 설명
IAPPayDelegate의 헤드 파일에 대해서는, Midas 공식 웹사이트 IAPPayDelegate 설명을 참조하십시오.
d) 반환값
없음
e) 예시 코드
//...
@interface LoginSucceedVC ()<IAPPayDelegate>
//...
@end
//...
[[IAPPayHelper getIntanceIapHelp] setDelegate:self];
-(void)parameterWrong:(NSString*)parameterLog
{
//결제 종료 환경 설정
WGPlatform::GetInstance()->WGEndGameStatus(((unsigned char*)"MSDKPayNotify"), -1, -1);
NSLog(@"callback:parameterWrong:%@",parameterLog);
}
//log의 콜백
-(void)log:(NSString*)message
{
NSLog(@"callback:logMessage:%@",message);
}
//로그인 상태 실패
-(void)onLoginExpiry:(RequestInfo*)info
{
//결제 종료 환경 설정
WGPlatform::GetInstance()->WGEndGameStatus(((unsigned char*)"MSDKPayNotify"), -1, -1);
NSLog(@"callback:login expire");
}
//주문 선공 콜백
-(void)onOrderFinish:(NSString*)billno withRequestInfo:(RequestInfo*)info
{
//결제 내 환경 설정
WGPlatform::GetInstance()->WGStartGameStatus((unsigned char*)"MSDKPayIng");
NSLog(@"callback:order succ");
}
//주문 실패 콜백(작업 오류)
-(void)onOrderFailue:(RequestInfo*)info withErrorMessage:(NSString*)errorMessage withErrorCode:(int)code
{
NSLog(@"callback:order fail");
}
//애플 결제 성공 콜백
-(void)onIAPPaymentSucess:(RequestInfo*)info
{
//결제 종료 환경 설정
WGPlatform::GetInstance()->WGEndGameStatus(((unsigned char*)"MSDKPayNotify"), 0, 0);
NSLog(@"callback: iap pay succ");
}
//품목 제품 정보 가져오기 실패
//제품을 가져올 때 제품 수량이 0인 경우에 대해
-(void)onGetProductInfoFailue:(RequestInfo*)info
{
//결제 종료 환경 설정
WGPlatform::GetInstance()->WGEndGameStatus(((unsigned char*)"MSDKPayNotify"), -1, -1);
NSLog(@"callback: get iap product info fail");
}
//애플 결제 실패 콜백
-(void)onIAPPayFailue:(RequestInfo*)info withError:(NSError*)error
{
//결제 종료 환경 설정
WGPlatform::GetInstance()->WGEndGameStatus(((unsigned char*)"MSDKPayNotify"), -1, -1);
NSLog(@"callback: iap pay fail, error info:%@", error);
}
//품목 발송 성공 콜백
-(void)onDistributeGoodsFinish:(RequestInfo*)info
{
NSLog(@"callback: distribute succ");
}
//품목 발송 실패 콜백(작업 오류)
//code=10001이면, 보충 발송이 필요하며, 그 밖의 오류는 불필요함
-(void)onDistributeGoodsFailue:(RequestInfo*)info withErrorMessage:(NSString*)errorMessage withErrorCode:(int)code
{
NSLog(@"callback: distribute fail");
}
3) 환경 변수 등록 및 보충 전송 인터페이스 등록
a) 기능 설명
환경 변수를 등록하는 동시에 보충 전송 인터페이스를 활성화하며 투명 전송 필드를 정의할 수도 있습니다.
b) 인터페이스 선언
-(BOOL)registerPay:(NSString*)offerid withOpenid:(NSString*)openid
withOpenKey:(NSString*)openKey
withSessionId:(NSString*)sessionId
withSessionType:(NSString*)sessionType
withPf:(NSString*)pf withPfkey:(NSString*)pfKey
withEnv:(NSString*)env withExtra:(NSDictionary *)dictExtra
c) 파라미터 설명
파라미터 명칭 | 파라미터 유형 | 설명 |
---|---|---|
offerid | String | offerid |
openid | String | 사용자 계정 id(account) |
openKey | String | 사용자 session이 모바일QQ는 paytoken, 위챗은 accesstoken |
sessionId | String | 사용자 계정 유형(uin 또는 openid) |
sessiontype | String | session 유형 모바일QQ는 kp_actoken, 위챗은 wc_actoken |
pf | String | pf |
pfkey | String | pfkey |
env | String | 지원환경은 test: 테스트 환경, release: 정식 환경 |
dictExtra | String | 작업 측에서 확장 필드 정의, kAppDefineInfo, kAppDefineInfo1, kAppDefineInfo2, kAppDefineInfo3 |
d) 반환값
파라미터 유형 | 설명 |
---|---|
bool | yes: 등록 성공, no: 등록 실패 |
e) 예시 코드
NSLog(@"결제 등록");
LoginRet ret;
WGPlatform* plat = WGPlatform::GetInstance();
int retCode = plat->WGGetLoginRecord(ret);
std::string openid = ret.open_id;
std::string paytoken;
std::string sessionId;
std::string sessionType;
if(retCode == ePlatform_QQ)
{
for(int i=0;i<ret.token.size();i++)
{
TokenRet* pToken = &ret.token[i];
if(pToken->type == eToken_QQ_Pay)
{
paytoken = pToken->value;
break;
}
}
sessionId = "openid";
sessionType = "kp_actoken";
}
else if (retCode == ePlatform_Weixin)
{
for(int i=0;i<ret.token.size();i++)
{
TokenRet* pToken = &ret.token[i];
if(pToken->type == eToken_WX_Access)
{
paytoken = pToken->value;
break;
}
}
sessionId = "hy_gameid";
sessionType = "wc_actoken";
}
else if (retCode == ePlatform_Guest)
{
for(int i=0;i<ret.token.size();i++)
{
TokenRet* pToken = &ret.token[i];
if(pToken->type == eToken_Guest_Access)
{
paytoken = pToken->value;
break;
}
}
sessionId = "hy_gameid";
sessionType = "st_dummy";
}
std::string pf = plat->WGGetPf();
std::string pfKey = plat->WGGetPfKey();
NSString *offerID = [MSDKInfoTool getOfferId];
NSDictionary *dictExtra = @{kAppExtra:@"1",kAppDefineInfo:@"1",kAppReserve1:@"1",kAppReserve2:@"1",kAppReserve3:@"1"};
[IAPPayHelper setIsEnLog:YES];
[IAPPayHelper setLocal:@"local"];
[[IAPPayHelper getIntanceIapHelp] setParentViewController:self];
[[IAPPayHelper getIntanceIapHelp] setDelegate:self];
[[IAPPayHelper getIntanceIapHelp]
registerPay:offerID
withOpenid:[NSString stringWithCString:openid.c_str() encoding:NSUTF8StringEncoding]
withOpenKey:[NSString stringWithCString:paytoken.c_str() encoding:NSUTF8StringEncoding]
withSessionId:[NSString stringWithCString:sessionId.c_str() encoding:NSUTF8StringEncoding]
withSessionType:[NSString stringWithCString:sessionType.c_str() encoding:NSUTF8StringEncoding]
withPf:[NSString stringWithCString:pf.c_str() encoding:NSUTF8StringEncoding]
withPfkey:[NSString stringWithCString:pfKey.c_str() encoding:NSUTF8StringEncoding]
withEnv:@"test"
withExtra:dictExtra];
4) 결제 인터페이스
a) 기능 설명
직접 IAP를 호출해 결제합니다.
b) 인터페이스 선언
-(void)pay:(NSString*)offerid
withOpenid:(NSString*)openid
withOpenKey:(NSString*)openKey
withSessionId:(NSString*)sessionId
withSessionType:(NSString*)sessionType
withPf:(NSString*)pf
withPfkey:(NSString*)pfKey
withPayItem:(NSString*)payItem
withProductId:(NSString*)productId
withIsDepositGameCoin:(Boolean)isDepositGameCoin
withProductType:(AppproductType)productType
withZoneId:(NSString*)zoneId
withVarItem:(NSString*)varItem
c) 파라미터 설명
파라미터 명칭 | 파라미터 유형 | 설명 |
---|---|---|
offerid | String | offerid |
openid | String | 사용자 계정 id(account) |
openKey | String | 사용자 session이 모바일QQ는 paytoken, 위챗은 accesstoken |
sessionId | String | 사용자 계정 유형(uin 또는 openid) |
sessiontype | String | session 유형 모바일QQ는 kp_actoken, 위챗은 wc_actoken |
pf | String | pf |
pfkey | String | pfkey |
payItem | String | 1. 애플리케이션이 도구 구매 유형의 결제 방식을 사용하는 경우, 해당 패러미터는 애플리케이션 측이 “물품 ID 단가(단위 “마오”(角)) 기준으로 수량”을 정의합니다. 2. 애플리케이션이 월정액 유형 결제 방식을 사용하는 경우, 월정액 개통 개월 수(QQ 회원이 이에 해당)를 전송합니다. 3. 게임 화폐 결제 방식인 경우, 충전된 게임 화폐의 갯수를 전송합니다. 4. 애플리케이션이 월별 카드 유형 결제 방식인 경우, 월별 카드 개통 후 지난 일 수를 전송합니다. 주의: 게임 화폐 방식이 전송하는 게임 화폐의 갯수는 전송되는 productID에 대응해야 합니다. 아래 그림과 같음 |
productId | String | 애플의 제품 id |
IsDepositGameCoin | bool | 수탁 여부, 게임 화폐 수탁: true, 직접 구매 또는 월정액: false |
productType | AppproductType | 애플 제품 유형 |
zoneId | String | 계정 구분 ID, 게임이 지원 캐릭터: zoneId인 경우, 분류 구역 ID_캐릭터ID |
(./res/midas_ios_purchase_payitem.png)
d) 반환값
없음
e) 예시 코드
LoginRet ret;
int retCode = plat->WGGetLoginRecord(ret);
std::string openid = ret.open_id;
std::string paytoken;
std::string sessionId;
std::string sessionType;
if(retCode == ePlatform_QQ)
{
for(int i=0;i<ret.token.size();i++)
{
TokenRet* pToken = &ret.token[i];
if(pToken->type == eToken_QQ_Pay)
{
paytoken = pToken->value;
break;
}
}
sessionId = "openid";
sessionType = "kp_actoken";
}
else if (retCode == ePlatform_Weixin)
{
for(int i=0;i<ret.token.size();i++)
{
TokenRet* pToken = &ret.token[i];
if(pToken->type == eToken_WX_Access)
{
paytoken = pToken->value;
break;
}
}
sessionId = "hy_gameid";
sessionType = "wc_actoken";
}
else if (retCode == ePlatform_Guest)
{
for(int i=0;i<ret.token.size();i++)
{
TokenRet* pToken = &ret.token[i];
if(pToken->type == eToken_Guest_Access)
{
paytoken = pToken->value;
break;
}
}
sessionId = "hy_gameid";
sessionType = "st_dummy";
}
std::string pf = plat->WGGetPf();
std::string pfKey = plat->WGGetPfKey();
NSString *offerID = [MSDKInfoTool getOfferId];
const char * payItem = PayPayitem;
const char * productId = PayProductid;
bool isDepositGameCoin = true;
uint32_t productType = 0;
const char * zoneId = "1";
const char * varItem = "com.lightspeed.weshoothd.600*1";
NSLog(@"\n\n\nofferid:%@\nopenid:%s\npaytoken:%s\nsessionId:%s\nsessionType:%s\npayItem:%s\nproductId:%s\npf:%s\npfKey:%s\nisDepositGameCoin:%d\nproductType:%d\nzoneId:%s\nvarItem:%s\n",offerID,openid.c_str(),paytoken.c_str(),sessionId.c_str(),
sessionType.c_str(),
payItem,
productId,
pf.c_str(),
pfKey.c_str(),
isDepositGameCoin,
productType,
zoneId,
varItem);
if (![IAPPayHelper judgeIsCanPay])
{
NSLog(@"can't pay in app");
return;
}
NSLog(@"\n\nMidasVersion:%@\n\n",[IAPPayHelper getVersion]);
//[[IAPPayHelper getIntanceIapHelp] setParentViewController:self];
// 결제 인터페이스 직접 호출
[[IAPPayHelper getIntanceIapHelp]
pay:offerID
withOpenid:[NSString stringWithCString:openid.c_str() encoding:NSUTF8StringEncoding]
withOpenKey:[NSString stringWithCString:paytoken.c_str() encoding:NSUTF8StringEncoding]
withSessionId:[NSString stringWithCString:sessionId.c_str() encoding:NSUTF8StringEncoding]
withSessionType:[NSString stringWithCString:sessionType.c_str() encoding:NSUTF8StringEncoding]
withPf:[NSString stringWithCString:pf.c_str() encoding:NSUTF8StringEncoding]
withPfkey:[NSString stringWithCString:pfKey.c_str() encoding:NSUTF8StringEncoding]
withPayItem:[NSString stringWithCString:payItem encoding:NSUTF8StringEncoding]
withProductId:[NSString stringWithCString:productId encoding:NSUTF8StringEncoding]
withIsDepositGameCoin:isDepositGameCoin
withProductType:Consumable
withZoneId:[NSString stringWithCString:zoneId encoding:NSUTF8StringEncoding]
withVarItem:[NSString stringWithCString:varItem encoding:NSUTF8StringEncoding]];
4 Midas 서버 인터페이스 액세스와 통합 및 테스트
Midas는 서버 호출 기능을 제공하는 결제 인터페이스로, 게임 화폐 잔액, 충전, 위탁, 마케팅 등을 수행할 수 있으며, 애플리케이션 서버는 내부/외부 방문 권한을 가지고 있어야 합니다. 상세 정보는 Midas 결제 API 통합 및 테스트를 참조해 주십시오.
5 온라인 결제 시 주의사항
제출 심사가 필요하며, 정식 환경 변환이 필요합니다. 온라인 방법-IAP를 참조하십시오.