Tests[UgradeUserToPro, DowngradeUserToNonPro, FailedUgradeUserToPro, FailToCreateProUser, ReuseProToken]
This commit is contained in:
parent
ec9a326002
commit
e7a45d9a05
@ -47,6 +47,8 @@
|
|||||||
|
|
||||||
- endpoint to list all servernames of user (distinct select)
|
- endpoint to list all servernames of user (distinct select)
|
||||||
|
|
||||||
|
- ios purchasw verification
|
||||||
|
|
||||||
#### PERSONAL
|
#### PERSONAL
|
||||||
|
|
||||||
- in my script: use `srvname` for sendername
|
- in my script: use `srvname` for sendername
|
||||||
|
@ -235,23 +235,30 @@ func (h APIHandler) UpdateUser(g *gin.Context) ginresp.HTTPResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if b.ProToken != nil {
|
if b.ProToken != nil {
|
||||||
ptok, err := h.app.VerifyProToken(ctx, *b.ProToken)
|
if *b.ProToken == "" {
|
||||||
if err != nil {
|
err := h.database.UpdateUserProToken(ctx, u.UserID, nil)
|
||||||
return ginresp.APIError(g, 500, apierr.FAILED_VERIFY_PRO_TOKEN, "Failed to query purchase status", err)
|
if err != nil {
|
||||||
}
|
return ginresp.APIError(g, 500, apierr.DATABASE_ERROR, "Failed to update user", err)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
ptok, err := h.app.VerifyProToken(ctx, *b.ProToken)
|
||||||
|
if err != nil {
|
||||||
|
return ginresp.APIError(g, 500, apierr.FAILED_VERIFY_PRO_TOKEN, "Failed to query purchase status", err)
|
||||||
|
}
|
||||||
|
|
||||||
if !ptok {
|
if !ptok {
|
||||||
return ginresp.APIError(g, 400, apierr.INVALID_PRO_TOKEN, "Purchase token could not be verified", nil)
|
return ginresp.APIError(g, 400, apierr.INVALID_PRO_TOKEN, "Purchase token could not be verified", nil)
|
||||||
}
|
}
|
||||||
|
|
||||||
err = h.database.ClearProTokens(ctx, *b.ProToken)
|
err = h.database.ClearProTokens(ctx, *b.ProToken)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ginresp.APIError(g, 500, apierr.DATABASE_ERROR, "Failed to clear existing fcm tokens", err)
|
return ginresp.APIError(g, 500, apierr.DATABASE_ERROR, "Failed to clear existing fcm tokens", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
err = h.database.UpdateUserProToken(ctx, u.UserID, b.ProToken)
|
err = h.database.UpdateUserProToken(ctx, u.UserID, b.ProToken)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ginresp.APIError(g, 500, apierr.DATABASE_ERROR, "Failed to update user", err)
|
return ginresp.APIError(g, 500, apierr.DATABASE_ERROR, "Failed to update user", err)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -810,12 +810,16 @@ func (h CompatHandler) Upgrade(g *gin.Context) ginresp.HTTPResponse {
|
|||||||
return ginresp.CompatAPIError(204, "Authentification failed")
|
return ginresp.CompatAPIError(204, "Authentification failed")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if data.ProToken != nil {
|
||||||
|
data.ProToken = langext.Ptr("ANDROID|v1|" + *data.ProToken)
|
||||||
|
}
|
||||||
|
|
||||||
if *data.Pro != "true" {
|
if *data.Pro != "true" {
|
||||||
data.ProToken = nil
|
data.ProToken = nil
|
||||||
}
|
}
|
||||||
|
|
||||||
if data.ProToken != nil {
|
if data.ProToken != nil {
|
||||||
ptok, err := h.app.VerifyProToken(ctx, "ANDROID|v1|"+*data.ProToken)
|
ptok, err := h.app.VerifyProToken(ctx, *data.ProToken)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ginresp.CompatAPIError(0, "Failed to query purchase status")
|
return ginresp.CompatAPIError(0, "Failed to query purchase status")
|
||||||
}
|
}
|
||||||
@ -824,7 +828,12 @@ func (h CompatHandler) Upgrade(g *gin.Context) ginresp.HTTPResponse {
|
|||||||
return ginresp.CompatAPIError(0, "Purchase token could not be verified")
|
return ginresp.CompatAPIError(0, "Purchase token could not be verified")
|
||||||
}
|
}
|
||||||
|
|
||||||
err = h.database.UpdateUserProToken(ctx, user.UserID, langext.Ptr("ANDROID|v1|"+*data.ProToken))
|
err = h.database.ClearProTokens(ctx, *data.ProToken)
|
||||||
|
if err != nil {
|
||||||
|
return ginresp.APIError(g, 500, apierr.DATABASE_ERROR, "Failed to clear existing fcm tokens", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
err = h.database.UpdateUserProToken(ctx, user.UserID, langext.Ptr(*data.ProToken))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ginresp.CompatAPIError(0, "Failed to update user")
|
return ginresp.CompatAPIError(0, "Failed to update user")
|
||||||
}
|
}
|
||||||
|
@ -130,6 +130,64 @@ func TestUpdateUsername(t *testing.T) {
|
|||||||
tt.AssertEqual(t, "username", nil, r6["username"])
|
tt.AssertEqual(t, "username", nil, r6["username"])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestUgradeUserToPro(t *testing.T) {
|
||||||
|
_, baseUrl, stop := tt.StartSimpleWebserver(t)
|
||||||
|
defer stop()
|
||||||
|
|
||||||
|
r0 := tt.RequestPost[gin.H](t, baseUrl, "/api/users", gin.H{
|
||||||
|
"no_client": true,
|
||||||
|
})
|
||||||
|
tt.AssertEqual(t, "is_pro", false, r0["is_pro"])
|
||||||
|
|
||||||
|
uid0 := fmt.Sprintf("%v", r0["user_id"])
|
||||||
|
admintok0 := r0["admin_key"].(string)
|
||||||
|
|
||||||
|
r1 := tt.RequestAuthPatch[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0, gin.H{"pro_token": "ANDROID|v2|PURCHASED:000"})
|
||||||
|
tt.AssertEqual(t, "is_pro", true, r1["is_pro"])
|
||||||
|
|
||||||
|
r2 := tt.RequestAuthGet[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0)
|
||||||
|
tt.AssertEqual(t, "is_pro", true, r2["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDowngradeUserToNonPro(t *testing.T) {
|
||||||
|
_, baseUrl, stop := tt.StartSimpleWebserver(t)
|
||||||
|
defer stop()
|
||||||
|
|
||||||
|
r0 := tt.RequestPost[gin.H](t, baseUrl, "/api/users", gin.H{
|
||||||
|
"no_client": true,
|
||||||
|
"pro_token": "ANDROID|v2|PURCHASED:UNIQ_111",
|
||||||
|
})
|
||||||
|
tt.AssertEqual(t, "is_pro", true, r0["is_pro"])
|
||||||
|
|
||||||
|
uid0 := fmt.Sprintf("%v", r0["user_id"])
|
||||||
|
admintok0 := r0["admin_key"].(string)
|
||||||
|
|
||||||
|
r1 := tt.RequestAuthPatch[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0, gin.H{"pro_token": ""})
|
||||||
|
tt.AssertEqual(t, "is_pro", false, r1["is_pro"])
|
||||||
|
|
||||||
|
r2 := tt.RequestAuthGet[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0)
|
||||||
|
tt.AssertEqual(t, "is_pro", false, r2["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestFailedUgradeUserToPro(t *testing.T) {
|
||||||
|
_, baseUrl, stop := tt.StartSimpleWebserver(t)
|
||||||
|
defer stop()
|
||||||
|
|
||||||
|
r0 := tt.RequestPost[gin.H](t, baseUrl, "/api/users", gin.H{
|
||||||
|
"no_client": true,
|
||||||
|
})
|
||||||
|
tt.AssertEqual(t, "is_pro", false, r0["is_pro"])
|
||||||
|
|
||||||
|
uid0 := fmt.Sprintf("%v", r0["user_id"])
|
||||||
|
admintok0 := r0["admin_key"].(string)
|
||||||
|
|
||||||
|
tt.RequestAuthPatchShouldFail(t, admintok0, baseUrl, "/api/users/"+uid0, gin.H{"pro_token": "ANDROID|v2|INVALID"}, 400, apierr.INVALID_PRO_TOKEN)
|
||||||
|
|
||||||
|
tt.RequestAuthPatchShouldFail(t, admintok0, baseUrl, "/api/users/"+uid0, gin.H{"pro_token": "ANDROID|v99|PURCHASED"}, 400, apierr.INVALID_PRO_TOKEN)
|
||||||
|
|
||||||
|
tt.RequestAuthPatchShouldFail(t, admintok0, baseUrl, "/api/users/"+uid0, gin.H{"pro_token": "@INVALID"}, 400, apierr.INVALID_PRO_TOKEN)
|
||||||
|
}
|
||||||
|
|
||||||
func TestRecreateKeys(t *testing.T) {
|
func TestRecreateKeys(t *testing.T) {
|
||||||
_, baseUrl, stop := tt.StartSimpleWebserver(t)
|
_, baseUrl, stop := tt.StartSimpleWebserver(t)
|
||||||
defer stop()
|
defer stop()
|
||||||
@ -259,30 +317,119 @@ func TestCreateProUser(t *testing.T) {
|
|||||||
tt.AssertEqual(t, "is_pro", true, r3["is_pro"])
|
tt.AssertEqual(t, "is_pro", true, r3["is_pro"])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestFailToCreateProUser(t *testing.T) {
|
||||||
|
_, baseUrl, stop := tt.StartSimpleWebserver(t)
|
||||||
|
defer stop()
|
||||||
|
|
||||||
|
tt.RequestPostShouldFail(t, baseUrl, "/api/users", gin.H{
|
||||||
|
"agent_model": "DUMMY_PHONE",
|
||||||
|
"agent_version": "4X",
|
||||||
|
"client_type": "ANDROID",
|
||||||
|
"fcm_token": "DUMMY_FCM",
|
||||||
|
"pro_token": "ANDROID|v2|INVALID",
|
||||||
|
}, 400, apierr.INVALID_PRO_TOKEN)
|
||||||
|
|
||||||
|
tt.RequestPostShouldFail(t, baseUrl, "/api/users", gin.H{
|
||||||
|
"agent_model": "DUMMY_PHONE",
|
||||||
|
"agent_version": "4X",
|
||||||
|
"client_type": "ANDROID",
|
||||||
|
"fcm_token": "DUMMY_FCM",
|
||||||
|
"pro_token": "_",
|
||||||
|
}, 400, apierr.INVALID_PRO_TOKEN)
|
||||||
|
|
||||||
|
tt.RequestPostShouldFail(t, baseUrl, "/api/users", gin.H{
|
||||||
|
"agent_model": "DUMMY_PHONE",
|
||||||
|
"agent_version": "4X",
|
||||||
|
"client_type": "ANDROID",
|
||||||
|
"fcm_token": "DUMMY_FCM",
|
||||||
|
"pro_token": "ANDROID|v99|xxx",
|
||||||
|
}, 400, apierr.INVALID_PRO_TOKEN)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestReuseProToken(t *testing.T) {
|
||||||
|
_, baseUrl, stop := tt.StartSimpleWebserver(t)
|
||||||
|
defer stop()
|
||||||
|
|
||||||
|
r0 := tt.RequestPost[gin.H](t, baseUrl, "/api/users", gin.H{
|
||||||
|
"no_client": true,
|
||||||
|
})
|
||||||
|
tt.AssertEqual(t, "is_pro", false, r0["is_pro"])
|
||||||
|
|
||||||
|
uid0 := fmt.Sprintf("%v", r0["user_id"])
|
||||||
|
admintok0 := r0["admin_key"].(string)
|
||||||
|
|
||||||
|
r1 := tt.RequestPost[gin.H](t, baseUrl, "/api/users", gin.H{
|
||||||
|
"no_client": true,
|
||||||
|
"pro_token": "ANDROID|v2|PURCHASED:UNIQ_1",
|
||||||
|
})
|
||||||
|
tt.AssertEqual(t, "is_pro", true, r1["is_pro"])
|
||||||
|
|
||||||
|
uid1 := fmt.Sprintf("%v", r1["user_id"])
|
||||||
|
admintok1 := r1["admin_key"].(string)
|
||||||
|
|
||||||
{
|
{
|
||||||
tt.RequestPostShouldFail(t, baseUrl, "/api/users", gin.H{
|
rc := tt.RequestAuthGet[gin.H](t, admintok1, baseUrl, "/api/users/"+uid1)
|
||||||
"agent_model": "DUMMY_PHONE",
|
tt.AssertEqual(t, "is_pro", true, rc["is_pro"])
|
||||||
"agent_version": "4X",
|
}
|
||||||
"client_type": "ANDROID",
|
|
||||||
"fcm_token": "DUMMY_FCM",
|
|
||||||
"pro_token": "ANDROID|v2|INVALID",
|
|
||||||
}, 400, apierr.INVALID_PRO_TOKEN)
|
|
||||||
|
|
||||||
tt.RequestPostShouldFail(t, baseUrl, "/api/users", gin.H{
|
r2 := tt.RequestPost[gin.H](t, baseUrl, "/api/users", gin.H{
|
||||||
"agent_model": "DUMMY_PHONE",
|
"no_client": true,
|
||||||
"agent_version": "4X",
|
"pro_token": "ANDROID|v2|PURCHASED:UNIQ_1",
|
||||||
"client_type": "ANDROID",
|
})
|
||||||
"fcm_token": "DUMMY_FCM",
|
tt.AssertEqual(t, "is_pro", true, r2["is_pro"])
|
||||||
"pro_token": "_",
|
|
||||||
}, 400, apierr.INVALID_PRO_TOKEN)
|
|
||||||
|
|
||||||
tt.RequestPostShouldFail(t, baseUrl, "/api/users", gin.H{
|
uid2 := fmt.Sprintf("%v", r2["user_id"])
|
||||||
"agent_model": "DUMMY_PHONE",
|
admintok2 := r2["admin_key"].(string)
|
||||||
"agent_version": "4X",
|
|
||||||
"client_type": "ANDROID",
|
{
|
||||||
"fcm_token": "DUMMY_FCM",
|
rc := tt.RequestAuthGet[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0)
|
||||||
"pro_token": "ANDROID|v99|xxx",
|
tt.AssertEqual(t, "is_pro", false, rc["is_pro"])
|
||||||
}, 400, apierr.INVALID_PRO_TOKEN)
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok1, baseUrl, "/api/users/"+uid1)
|
||||||
|
tt.AssertEqual(t, "is_pro", false, rc["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok2, baseUrl, "/api/users/"+uid2)
|
||||||
|
tt.AssertEqual(t, "is_pro", true, rc["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
tt.RequestAuthPatch[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0, gin.H{"pro_token": "ANDROID|v2|PURCHASED:UNIQ_2"})
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0)
|
||||||
|
tt.AssertEqual(t, "is_pro", true, rc["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok1, baseUrl, "/api/users/"+uid1)
|
||||||
|
tt.AssertEqual(t, "is_pro", false, rc["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok2, baseUrl, "/api/users/"+uid2)
|
||||||
|
tt.AssertEqual(t, "is_pro", true, rc["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
tt.RequestAuthPatch[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0, gin.H{"pro_token": "ANDROID|v2|PURCHASED:UNIQ_1"})
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok0, baseUrl, "/api/users/"+uid0)
|
||||||
|
tt.AssertEqual(t, "is_pro", true, rc["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok1, baseUrl, "/api/users/"+uid1)
|
||||||
|
tt.AssertEqual(t, "is_pro", false, rc["is_pro"])
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
rc := tt.RequestAuthGet[gin.H](t, admintok2, baseUrl, "/api/users/"+uid2)
|
||||||
|
tt.AssertEqual(t, "is_pro", false, rc["is_pro"])
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user