X-Git-Url: http://de.git.xonotic.org/?p=xonotic%2Fxonotic-data.pk3dir.git;a=blobdiff_plain;f=qcsrc%2Fcommon%2Fplayerstats.qc;h=5890fb89e17085271e6061684e3792a6bcc0a735;hp=5eaecc75c344b222a7a355fd09f7e5a15802a59a;hb=77f03e6ce033bef39ac19e0e7cb6e606ffcb26db;hpb=53c9348aa146e7da4c06c0199d2955cd7d1d433b diff --git a/qcsrc/common/playerstats.qc b/qcsrc/common/playerstats.qc index 5eaecc75c..5890fb89e 100644 --- a/qcsrc/common/playerstats.qc +++ b/qcsrc/common/playerstats.qc @@ -1,3 +1,18 @@ +#if defined(CSQC) +#elif defined(MENUQC) +#elif defined(SVQC) + #include "../dpdefs/progsdefs.qh" + #include "../dpdefs/dpextensions.qh" + #include "constants.qh" + #include "util.qh" + #include "urllib.qh" + #include "weapons/weapons.qh" + #include "../server/weapons/accuracy.qh" + #include "../server/defs.qh" + #include "playerstats.qh" + #include "../server/scores.qh" +#endif + #ifdef SVQC void PlayerStats_Prematch(void) { @@ -15,7 +30,7 @@ void PlayerStats_GameReport_AddPlayer(entity e) { s = e.crypto_idfp; } else if(IS_BOT_CLIENT(e)) { s = sprintf("bot#%g#%s", skill, e.cleanname); } - + if((s == "") || find(world, playerstats_id, s)) // already have one of the ID - next one can't be tracked then! { if(IS_BOT_CLIENT(e)) @@ -23,13 +38,13 @@ void PlayerStats_GameReport_AddPlayer(entity e) else { s = sprintf("player#%d", e.playerid); } } - + e.playerstats_id = strzone(s); // now add the player to the database string key = sprintf("%s:*", e.playerstats_id); string p = db_get(PS_GR_OUT_DB, key); - + if(p == "") { if(PS_GR_OUT_PL) @@ -48,7 +63,7 @@ void PlayerStats_GameReport_AddTeam(float t) string key = sprintf("%d", t); string p = db_get(PS_GR_OUT_DB, key); - + if(p == "") { if(PS_GR_OUT_TL) @@ -67,7 +82,7 @@ void PlayerStats_GameReport_AddEvent(string event_id) string key = sprintf("*:%s", event_id); string p = db_get(PS_GR_OUT_DB, key); - + if(p == "") { if(PS_GR_OUT_EVL) @@ -94,12 +109,11 @@ float PlayerStats_GameReport_Event(string prefix, string event_id, float value) void PlayerStats_GameReport_Accuracy(entity p) { - entity w; - float i; + int i; for(i = WEP_FIRST; i <= WEP_LAST; ++i) { - w = get_weaponinfo(i); + entity w = get_weaponinfo(i); #define ACCMAC(suffix,field) \ PS_GR_P_ADDVAL(p, sprintf("acc-%s-%s", w.netname, suffix), p.accuracy.(field[i-1])); @@ -154,7 +168,7 @@ void PlayerStats_GameReport_FinalizePlayer(entity p) void PlayerStats_GameReport(float finished) { if(PS_GR_OUT_DB < 0) { return; } - + PlayerScore_Sort(score_dummyfield, 0, 0, 0); PlayerScore_Sort(scoreboard_pos, 1, 1, 1); if(teamplay) { PlayerScore_TeamStats(); } @@ -191,7 +205,7 @@ void PlayerStats_GameReport(float finished) if(autocvar_g_playerstats_gamereport_uri != "") { - PlayerStats_GameReport_DelayMapVote = TRUE; + PlayerStats_GameReport_DelayMapVote = true; url_multi_fopen( autocvar_g_playerstats_gamereport_uri, FILE_APPEND, @@ -201,7 +215,7 @@ void PlayerStats_GameReport(float finished) } else { - PlayerStats_GameReport_DelayMapVote = FALSE; + PlayerStats_GameReport_DelayMapVote = false; db_close(PS_GR_OUT_DB); PS_GR_OUT_DB = -1; } @@ -211,12 +225,11 @@ void PlayerStats_GameReport_Init() // initiated before InitGameplayMode so that { if(autocvar_g_playerstats_gamereport_uri == "") { return; } - PS_GR_OUT_DB = -1; PS_GR_OUT_DB = db_create(); if(PS_GR_OUT_DB >= 0) { - PlayerStats_GameReport_DelayMapVote = TRUE; + PlayerStats_GameReport_DelayMapVote = true; serverflags |= SERVERFLAG_PLAYERSTATS; @@ -253,7 +266,7 @@ void PlayerStats_GameReport_Init() // initiated before InitGameplayMode so that PlayerStats_GameReport_AddEvent(PLAYERSTATS_ACHIEVEMENT_FIRSTBLOOD); PlayerStats_GameReport_AddEvent(PLAYERSTATS_ACHIEVEMENT_FIRSTVICTIM); } - else { PlayerStats_GameReport_DelayMapVote = FALSE; } + else { PlayerStats_GameReport_DelayMapVote = false; } } void PlayerStats_GameReport_Handler(entity fh, entity pass, float status) @@ -349,7 +362,7 @@ void PlayerStats_GameReport_Handler(entity fh, entity pass, float status) nn = db_get(PS_GR_OUT_DB, sprintf("%s:_playerid", p)); if(nn != "") { url_fputs(fh, sprintf("i %s\n", nn)); } - // player name + // player name nn = db_get(PS_GR_OUT_DB, sprintf("%s:_netname", p)); if(nn != "") { url_fputs(fh, sprintf("n %s\n", nn)); } @@ -382,18 +395,18 @@ void PlayerStats_GameReport_Handler(entity fh, entity pass, float status) { // url_fclose is processing, we got a response for writing the data // this must come from HTTP - print("Got response from player stats server:\n"); - while((s = url_fgets(fh))) { print(" ", s, "\n"); } - print("End of response.\n"); + dprint("Got response from player stats server:\n"); + while((s = url_fgets(fh))) { dprint(" ", s, "\n"); } + dprint("End of response.\n"); url_fclose(fh); break; } - + case URL_READY_CLOSED: { // url_fclose has finished - print("Player stats written\n"); - PlayerStats_GameReport_DelayMapVote = FALSE; + dprint("Player stats written\n"); + PlayerStats_GameReport_DelayMapVote = false; if(PS_GR_OUT_DB >= 0) { db_close(PS_GR_OUT_DB); @@ -401,12 +414,12 @@ void PlayerStats_GameReport_Handler(entity fh, entity pass, float status) } break; } - + case URL_READY_ERROR: default: { print("Player stats writing failed: ", ftos(status), "\n"); - PlayerStats_GameReport_DelayMapVote = FALSE; + PlayerStats_GameReport_DelayMapVote = false; if(PS_GR_OUT_DB >= 0) { db_close(PS_GR_OUT_DB); @@ -417,35 +430,76 @@ void PlayerStats_GameReport_Handler(entity fh, entity pass, float status) } } -void PlayerStats_PlayerBasic() +void PlayerStats_PlayerBasic(entity joiningplayer, float newrequest) { - entity player; - //PS_D_IN_DB = -1; - //PS_D_IN_DB = db_create(); - - //if(PS_D_IN_DB < 0) { return; } - - FOR_EACH_REALCLIENT(player) + // http://stats.xonotic.org/player/GgXRw6piDtFIbMArMuiAi8JG4tiin8VLjZgsKB60Uds=/elo.txt + if(autocvar_g_playerstats_playerbasic_uri != "") { string uri = autocvar_g_playerstats_playerbasic_uri; - if((uri != "") && (player.crypto_idfp != "")) + if(joiningplayer.crypto_idfp != "") { - uri = strcat(uri, "/player/", uri_escape(uri_escape(player.crypto_idfp)), "/elo.txt"); - print("Retrieving playerstats from URL: ", uri, "\n"); + // create the database if it doesn't already exist + if(PS_B_IN_DB < 0) + PS_B_IN_DB = db_create(); + + // now request the information + uri = strcat(uri, "/player/", uri_escape(uri_escape(joiningplayer.crypto_idfp)), "/elo.txt"); + dprint("Retrieving playerstats from URL: ", uri, "\n"); url_single_fopen( uri, FILE_APPEND, PlayerStats_PlayerBasic_Handler, - player + joiningplayer ); - } - /*p.crypto_idfp != "") + // set status appropriately // todo: check whether the player info exists in the database previously + if(newrequest) + { + // database still contains useful information, so don't clear it of a useful status + joiningplayer.playerstats_basicstatus = PS_B_STATUS_WAITING; + } + else + { + // database was previously empty or never hit received status for some reason + joiningplayer.playerstats_basicstatus = PS_B_STATUS_UPDATING; + } + } + } + else + { + // server has this disabled, kill the DB and set status to idle + if(PS_B_IN_DB >= 0) { - uri = strcat(uri, "/elo/", uri_escape(p.crypto_idfp)); - print("Retrieving playerstats from URL: ", uri, "\n"); - url_single_fopen(uri, FILE_READ, PlayerInfo_ready, p); - }*/ + entity player; + + db_close(PS_B_IN_DB); + PS_B_IN_DB = -1; + + FOR_EACH_REALCLIENT(player) { player.playerstats_basicstatus = PS_B_STATUS_IDLE; } + } + } +} + +void PlayerStats_PlayerBasic_CheckUpdate(entity joiningplayer) +{ + // determine whether we should retrieve playerbasic information again + + #if 0 + printf("PlayerStats_PlayerBasic_CheckUpdate('%s'): %f\n", + joiningplayer.netname, + time + ); + #endif + + // TODO: check to see if this playerid is inside the database already somehow... + // for now we'll just check the field, but this won't work for players who disconnect and reconnect properly + // although maybe we should just submit another request ANYWAY? + if(!joiningplayer.playerstats_basicstatus) + { + PlayerStats_PlayerBasic( + joiningplayer, + (joiningplayer.playerstats_basicstatus == PS_B_STATUS_RECEIVED) + ); } } @@ -455,29 +509,29 @@ void PlayerStats_PlayerBasic_Handler(entity fh, entity p, float status) { case URL_READY_CANWRITE: { - print("-- Sending data to player stats server\n"); + dprint("-- Sending data to player stats server\n"); /*url_fputs(fh, "V 1\n"); #ifdef WATERMARK url_fputs(fh, sprintf("R %s\n", WATERMARK)); #endif url_fputs(fh, sprintf("l %s\n", cvar_string("_menu_prvm_language"))); // language url_fputs(fh, sprintf("c %s\n", cvar_string("_menu_prvm_country"))); // country - url_fputs(fh, sprintf("g %s\n", cvar_string("_menu_prvm_gender"))); // gender + url_fputs(fh, sprintf("g %s\n", cvar_string("_cl_gender"))); // gender url_fputs(fh, sprintf("n %s\n", cvar_string("_cl_name"))); // name url_fputs(fh, sprintf("m %s %s\n", cvar_string("_cl_playermodel"), cvar_string("_cl_playerskin"))); // model/skin */url_fputs(fh, "\n"); url_fclose(fh); break; } - + case URL_READY_CANREAD: { string s = ""; - print("-- Got response from player stats server:\n"); + dprint("-- Got response from player stats server:\n"); //string gametype = string_null; while((s = url_fgets(fh))) { - print(" ", s, "\n"); + dprint(" ", s, "\n"); /* string key = "", value = "", data = ""; @@ -528,7 +582,7 @@ void PlayerStats_PlayerBasic_Handler(entity fh, entity p, float status) continue; */ } - print("-- End of response.\n"); + dprint("-- End of response.\n"); url_fclose(fh); break; } @@ -538,7 +592,7 @@ void PlayerStats_PlayerBasic_Handler(entity fh, entity p, float status) print("Player stats synchronized with server\n"); break; } - + case URL_READY_ERROR: default: { @@ -575,28 +629,26 @@ void PlayerStats_PlayerDetail_AddItem(string event, string data) db_put(PS_D_IN_DB, marker, PS_D_IN_EVL); strunzone(PS_D_IN_EVL); } - else { db_put(PS_D_IN_DB, marker, "#"); } + else { db_put(PS_D_IN_DB, marker, "#"); } PS_D_IN_EVL = strzone(marker); } // now actually set the event data db_put(PS_D_IN_DB, sprintf("#%s", event), data); - print("Added item ", sprintf("#%s", event), "=", data, " to PS_D_IN_DB\n"); + dprint("Added item ", sprintf("#%s", event), "=", data, " to PS_D_IN_DB\n"); } void PlayerStats_PlayerDetail(void) { + // http://stats.xonotic.org/player/me if((autocvar_g_playerstats_playerdetail_uri != "") && (crypto_getmyidstatus(0) > 0)) { // create the database if it doesn't already exist if(PS_D_IN_DB < 0) - { - PS_D_IN_DB = -1; PS_D_IN_DB = db_create(); - } //uri = strcat(uri, "/player/", uri_escape(crypto_getmyidfp(0))); - print("Retrieving playerstats from URL: ", autocvar_g_playerstats_playerdetail_uri, "\n"); + dprint("Retrieving playerstats from URL: ", autocvar_g_playerstats_playerdetail_uri, "\n"); url_single_fopen( autocvar_g_playerstats_playerdetail_uri, FILE_APPEND, @@ -624,12 +676,14 @@ void PlayerStats_PlayerDetail_CheckUpdate(void) // determine whether we should retrieve playerdetail information again float gamecount = cvar("cl_matchcount"); + #if 0 printf("PlayerStats_PlayerDetail_CheckUpdate(): %f >= %f, %d > %d\n", time, PS_D_NEXTUPDATETIME, PS_D_LASTGAMECOUNT, gamecount ); + #endif if( (time >= PS_D_NEXTUPDATETIME) @@ -649,7 +703,7 @@ void PlayerStats_PlayerDetail_Handler(entity fh, entity unused, float status) { case URL_READY_CANWRITE: { - print("PlayerStats_PlayerDetail_Handler(): Sending data to player stats server...\n"); + dprint("PlayerStats_PlayerDetail_Handler(): Sending data to player stats server...\n"); url_fputs(fh, "V 1\n"); #ifdef WATERMARK url_fputs(fh, sprintf("R %s\n", WATERMARK)); @@ -663,7 +717,7 @@ void PlayerStats_PlayerDetail_Handler(entity fh, entity unused, float status) url_fclose(fh); break; } - + case URL_READY_CANREAD: { //print("PlayerStats_PlayerDetail_Handler(): Got response from player stats server:\n"); @@ -675,7 +729,7 @@ void PlayerStats_PlayerDetail_Handler(entity fh, entity unused, float status) string key = "", event = "", data = ""; if(argv(0) == "#") { continue; } - + if(count == 2) { key = argv(0); @@ -719,12 +773,17 @@ void PlayerStats_PlayerDetail_Handler(entity fh, entity unused, float status) } break; } - + default: { - print( + printf( "PlayerStats_PlayerDetail_Handler(): ERROR: " "Key went unhandled? Is our version outdated?\n" + "PlayerStats_PlayerDetail_Handler(): " + "Key '%s', Event '%s', Data '%s'\n", + key, + event, + data ); break; } @@ -732,7 +791,8 @@ void PlayerStats_PlayerDetail_Handler(entity fh, entity unused, float status) #if 0 print(sprintf( - "PlayerStats_PlayerDetail_Handler(): Key '%s', Event '%s', Data '%s'\n", + "PlayerStats_PlayerDetail_Handler(): " + "Key '%s', Event '%s', Data '%s'\n", key, event, data @@ -856,7 +916,7 @@ void PlayerInfo_ready(entity fh, entity p, float status) #ifdef MENUQC url_fputs(fh, sprintf("l %s\n", cvar_string("_menu_prvm_language"))); // language url_fputs(fh, sprintf("c %s\n", cvar_string("_menu_prvm_country"))); // country - url_fputs(fh, sprintf("g %s\n", cvar_string("_menu_prvm_gender"))); // gender + url_fputs(fh, sprintf("g %s\n", cvar_string("_cl_gender"))); // gender url_fputs(fh, sprintf("n %s\n", cvar_string("_cl_name"))); // name url_fputs(fh, sprintf("m %s %s\n", cvar_string("_cl_playermodel"), cvar_string("_cl_playerskin"))); // model/skin #endif @@ -934,7 +994,6 @@ void PlayerInfo_ready(entity fh, entity p, float status) void PlayerInfo_Init() { - playerinfo_db = -1; playerinfo_db = db_create(); } @@ -979,7 +1038,7 @@ void PlayerInfo_Details() #ifdef CSQC /* - * FIXME - crypto_* builtin functions missing in CSQC (csprogsdefs.qc:885) + * FIXME - crypto_* builtin functions missing in CSQC (csprogsdefs.qh:885) void PlayerInfo_Details() { print("-- Getting detailed PlayerInfo for local player (CSQC)\n");