OpenTTD Source: src/network/network_survey.cpp Source File

OpenTTD Source 15.0-RC2

network_survey.cpp
Go to the documentation of this file.
1/*
2 * This file is part of OpenTTD.
3 * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2.
4 * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
5 * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <https://www.gnu.org/licenses/old-licenses/gpl-2.0>.
6 */
7
10#include "../stdafx.h"
11#include "network_survey.h"
12#include "../settings_table.h"
13#include "network.h"
14#include "network_func.h"
15#include "../debug.h"
16#include "../survey.h"
17#include "../3rdparty/fmt/chrono.h"
18#include "../3rdparty/fmt/std.h"
19
20#include "../safeguards.h"
21
22 NetworkSurveyHandler _survey = {};
23
24NLOHMANN_JSON_SERIALIZE_ENUM(NetworkSurveyHandler::Reason, {
25 {NetworkSurveyHandler::Reason::PREVIEW, "preview"},
26 {NetworkSurveyHandler::Reason::LEAVE, "leave"},
27 {NetworkSurveyHandler::Reason::EXIT, "exit"},
28 {NetworkSurveyHandler::Reason::CRASH, "crash"},
29})
30
38std::string NetworkSurveyHandler::CreatePayload(Reason reason, bool for_preview)
39{
40 nlohmann::json survey;
41
42 survey["schema"] = NETWORK_SURVEY_VERSION;
43 survey["reason"] = reason;
44 survey["date"] = fmt::format("{:%Y-%m-%d %H:%M:%S} (UTC)", fmt::gmtime(time(nullptr)));
45
46#ifdef SURVEY_KEY
47 /* We censor the key to avoid people trying to be "clever" and use it to send their own surveys. */
48 survey["key"] = for_preview ? "(redacted)" : SURVEY_KEY;
49#else
50 survey["key"] = "";
51#endif
52
53 SurveyGameSession(survey["session"]);
54
55 {
56 auto &info = survey["info"];
57 SurveyOS(info["os"]);
58 SurveyOpenTTD(info["openttd"]);
59 SurveyConfiguration(info["configuration"]);
60 SurveyFont(info["font"]);
61 SurveyCompiler(info["compiler"]);
62 SurveyLibraries(info["libraries"]);
63 SurveyPlugins(info["plugins"]);
64 }
65
66 {
67 auto &game = survey["game"];
68 SurveyTimers(game["timers"]);
69 SurveyCompanies(game["companies"]);
70 SurveySettings(game["settings"], false);
71 SurveyGrfs(game["grfs"]);
72 SurveyGameScript(game["game_script"]);
73 }
74
75 /* For preview, we indent with 4 whitespaces to make things more readable. */
76 int indent = for_preview ? 4 : -1;
77 return survey.dump(indent);
78}
79
86 void NetworkSurveyHandler::Transmit(Reason reason, bool blocking)
87{
88 if constexpr (!NetworkSurveyHandler::IsSurveyPossible()) {
89 Debug(net, 4, "Survey: not possible to send survey; most likely due to missing JSON library at compile-time");
90 return;
91 }
92
93 if (_settings_client.network.participate_survey != PS_YES) {
94 Debug(net, 5, "Survey: user is not participating in survey; skipping survey");
95 return;
96 }
97
98 Debug(net, 1, "Survey: sending survey results");
99 NetworkHTTPSocketHandler::Connect(NetworkSurveyUriString(), this, this->CreatePayload(reason));
100
101 if (blocking) {
102 std::unique_lock<std::mutex> lock(this->mutex);
103
104 /* Block no longer than 2 seconds. If we failed to send the survey in that time, so be it. */
105 std::chrono::steady_clock::time_point end = std::chrono::steady_clock::now() + std::chrono::seconds(2);
106
107 while (!this->transmitted && std::chrono::steady_clock::now() < end) {
108 NetworkBackgroundLoop();
109 this->transmitted_cv.wait_for(lock, std::chrono::milliseconds(30));
110 }
111 }
112}
113
114 void NetworkSurveyHandler::OnFailure()
115{
116 Debug(net, 1, "Survey: failed to send survey results");
117 this->transmitted = true;
118 this->transmitted_cv.notify_all();
119}
120
121 void NetworkSurveyHandler::OnReceiveData(std::unique_ptr<char[]> data, size_t)
122{
123 if (data == nullptr) {
124 Debug(net, 1, "Survey: survey results sent");
125 this->transmitted = true;
126 this->transmitted_cv.notify_all();
127 }
128}
NetworkHTTPSocketHandler::Connect
static void Connect(std::string_view uri, HTTPCallback *callback, std::string &&data="")
Connect to the given URI.
Definition http_curl.cpp:93
NetworkSurveyHandler
Socket handler for the survey connection.
Definition network_survey.h:20
NetworkSurveyHandler::OnFailure
void OnFailure() override
An error has occurred and the connection has been closed.
Definition network_survey.cpp:114
NetworkSurveyHandler::transmitted
std::atomic< bool > transmitted
Whether the survey has been transmitted.
Definition network_survey.h:44
NetworkSurveyHandler::transmitted_cv
std::condition_variable transmitted_cv
Condition variable to inform changes to transmitted.
Definition network_survey.h:45
NetworkSurveyHandler::OnReceiveData
void OnReceiveData(std::unique_ptr< char[]> data, size_t length) override
We're receiving data.
Definition network_survey.cpp:121
NetworkSurveyHandler::Reason
Reason
Definition network_survey.h:27
NetworkSurveyHandler::Reason::PREVIEW
@ PREVIEW
User is previewing the survey result.
NetworkSurveyHandler::Reason::EXIT
@ EXIT
User is exiting the application.
NetworkSurveyHandler::Reason::CRASH
@ CRASH
Game crashed.
NetworkSurveyHandler::Reason::LEAVE
@ LEAVE
User is leaving the game (but not exiting the application).
NetworkSurveyHandler::mutex
std::mutex mutex
Mutex for the condition variable.
Definition network_survey.h:43
NetworkSurveyHandler::Transmit
void Transmit(Reason reason, bool blocking=false)
Transmit the survey.
Definition network_survey.cpp:86
NetworkSurveyUriString
std::string_view NetworkSurveyUriString()
Get the URI string for the survey from the environment variable OTTD_SURVEY_URI, or when it has not b...
Definition config.cpp:63
NETWORK_SURVEY_VERSION
static const uint8_t NETWORK_SURVEY_VERSION
What version of the survey do we use?
Definition config.h:51
Debug
#define Debug(category, level, format_string,...)
Output a line of debugging information.
Definition debug.h:37
NetworkBackgroundLoop
void NetworkBackgroundLoop()
We have to do some (simple) background stuff that runs normally, even when we are not in multiplayer.
Definition network.cpp:1080
network.h
Basic functions/variables used all over the place.
network_func.h
Network functions used by other parts of OpenTTD.
NLOHMANN_JSON_SERIALIZE_ENUM
NLOHMANN_JSON_SERIALIZE_ENUM(NetworkSurveyHandler::Reason, { {NetworkSurveyHandler::Reason::PREVIEW, "preview"}, {NetworkSurveyHandler::Reason::LEAVE, "leave"}, {NetworkSurveyHandler::Reason::EXIT, "exit"}, {NetworkSurveyHandler::Reason::CRASH, "crash"}, }) std
Create the payload for the survey.
Definition network_survey.cpp:24
network_survey.h
Part of the network protocol handling opt-in survey.
_settings_client
ClientSettings _settings_client
The current settings for this game.
Definition settings.cpp:60
ClientSettings::network
NetworkSettings network
settings related to the network
Definition settings_type.h:651
NetworkSettings::participate_survey
ParticipateSurvey participate_survey
Participate in the automated survey.
Definition settings_type.h:372
SurveySettings
void SurveySettings(nlohmann::json &survey, bool skip_if_default)
Convert settings to JSON.
Definition survey.cpp:164
SurveyPlugins
void SurveyPlugins(nlohmann::json &survey)
Convert plugin information to JSON.
Definition survey.cpp:465
SurveyTimers
void SurveyTimers(nlohmann::json &survey)
Convert timer information to JSON.
Definition survey.cpp:343
SurveyGameSession
void SurveyGameSession(nlohmann::json &survey)
Convert game session information to JSON.
Definition survey.cpp:242
SurveyGameScript
void SurveyGameScript(nlohmann::json &survey)
Convert game-script information to JSON.
Definition survey.cpp:386
SurveyConfiguration
void SurveyConfiguration(nlohmann::json &survey)
Convert generic game information to JSON.
Definition survey.cpp:256
SurveyOpenTTD
void SurveyOpenTTD(nlohmann::json &survey)
Convert generic OpenTTD information to JSON.
Definition survey.cpp:210
SurveyFont
void SurveyFont(nlohmann::json &survey)
Convert font information to JSON.
Definition survey.cpp:299
SurveyCompanies
void SurveyCompanies(nlohmann::json &survey)
Convert company information to JSON.
Definition survey.cpp:312
SurveyCompiler
void SurveyCompiler(nlohmann::json &survey)
Convert compiler information to JSON.
Definition survey.cpp:182
SurveyLibraries
void SurveyLibraries(nlohmann::json &survey)
Convert compiled libraries information to JSON.
Definition survey.cpp:398
SurveyGrfs
void SurveyGrfs(nlohmann::json &survey)
Convert GRF information to JSON.
Definition survey.cpp:359
lock
std::mutex lock
synchronization for playback status fields
Definition win32_m.cpp:35