mirror of
https://github.com/kidfromjupiter/nearby.git
synced 2026-09-15 07:06:11 -04:00
Add onSessionComplete method in ClientProxy to log session
PiperOrigin-RevId: 461772377
This commit is contained in:
@@ -234,6 +234,7 @@ cc_test(
|
||||
"//connections:core_types",
|
||||
"//connections/implementation/mediums",
|
||||
"//connections/implementation/proto:offline_wire_formats_cc_proto",
|
||||
"//internal/analytics:event_logger",
|
||||
"//internal/platform:base",
|
||||
"//internal/platform:comm",
|
||||
"//internal/platform:logging",
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
|
||||
#include <algorithm>
|
||||
#include <memory>
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <utility>
|
||||
|
||||
@@ -33,6 +34,7 @@ namespace analytics {
|
||||
|
||||
namespace {
|
||||
const char kVersion[] = "v1.0.0";
|
||||
constexpr absl::string_view kOnStartClientSession = "OnStartClientSession";
|
||||
} // namespace
|
||||
|
||||
using ::location::nearby::analytics::proto::ConnectionsLog;
|
||||
@@ -88,21 +90,41 @@ using ::nearby::analytics::EventLogger;
|
||||
|
||||
AnalyticsRecorder::AnalyticsRecorder(EventLogger *event_logger)
|
||||
: event_logger_(event_logger) {
|
||||
started_client_session_time_ = SystemClock::ElapsedRealtime();
|
||||
NEARBY_LOGS(INFO) << "AnalyticsRecorder ctor event_logger_=" << event_logger_;
|
||||
MutexLock lock(&mutex_);
|
||||
if (CanRecordAnalyticsLocked("OnStartClientSession")) {
|
||||
LogEvent(START_CLIENT_SESSION);
|
||||
}
|
||||
NEARBY_LOGS(INFO) << "Start AnalyticsRecorder ctor event_logger_="
|
||||
<< event_logger_;
|
||||
LogStartSession();
|
||||
}
|
||||
|
||||
AnalyticsRecorder::~AnalyticsRecorder() {
|
||||
serial_executor_.Shutdown();
|
||||
ResetClientSessionLoggingResouces();
|
||||
}
|
||||
|
||||
bool AnalyticsRecorder::IsSessionLogged() {
|
||||
MutexLock lock(&mutex_);
|
||||
return session_was_logged_;
|
||||
}
|
||||
|
||||
void AnalyticsRecorder::ResetClientSessionLoggingResouces() {
|
||||
MutexLock lock(&mutex_);
|
||||
NEARBY_LOGS(INFO) << "Reset AnalyticsRecorder ctor event_logger_="
|
||||
<< event_logger_;
|
||||
|
||||
incoming_connection_requests_.clear();
|
||||
outgoing_connection_requests_.clear();
|
||||
active_connections_.clear();
|
||||
bandwidth_upgrade_attempts_.clear();
|
||||
serial_executor_.Shutdown();
|
||||
|
||||
client_session_ = nullptr;
|
||||
session_was_logged_ = true;
|
||||
start_client_session_was_logged_ = false;
|
||||
current_strategy_ =
|
||||
connections::Strategy::kNone; // Need to reset since the same strategy
|
||||
// should be logged separately for
|
||||
// different client sessions.
|
||||
current_strategy_session_ = nullptr;
|
||||
current_advertising_phase_ = nullptr;
|
||||
current_discovery_phase_ = nullptr;
|
||||
}
|
||||
|
||||
void AnalyticsRecorder::OnStartAdvertising(
|
||||
@@ -163,8 +185,7 @@ void AnalyticsRecorder::OnStartDiscovery(
|
||||
|
||||
// Initialize and set a DiscoveryPhase.
|
||||
started_discovery_phase_time_ = SystemClock::ElapsedRealtime();
|
||||
current_discovery_phase_ =
|
||||
std::make_unique<ConnectionsLog::DiscoveryPhase>();
|
||||
current_discovery_phase_ = std::make_unique<ConnectionsLog::DiscoveryPhase>();
|
||||
absl::c_copy(mediums, RepeatedFieldBackInserter(
|
||||
current_discovery_phase_->mutable_medium()));
|
||||
// Set a DiscoveryMetadata.
|
||||
@@ -632,6 +653,26 @@ void AnalyticsRecorder::OnErrorCode(const ErrorCodeParams ¶ms) {
|
||||
});
|
||||
}
|
||||
|
||||
void AnalyticsRecorder::LogStartSession() {
|
||||
MutexLock lock(&mutex_);
|
||||
if (start_client_session_was_logged_) {
|
||||
NEARBY_LOGS(WARNING)
|
||||
<< "AnalyticsRecorder CanRecordAnalytics Unexpected call "
|
||||
<< kOnStartClientSession
|
||||
<< " after start client session has already been logged.";
|
||||
return;
|
||||
}
|
||||
|
||||
session_was_logged_ = false;
|
||||
if (CanRecordAnalyticsLocked(kOnStartClientSession)) {
|
||||
client_session_ =
|
||||
std::make_unique<proto::ConnectionsLog::ClientSession>();
|
||||
started_client_session_time_ = SystemClock::ElapsedRealtime();
|
||||
start_client_session_was_logged_ = true;
|
||||
LogEvent(START_CLIENT_SESSION);
|
||||
}
|
||||
}
|
||||
|
||||
void AnalyticsRecorder::LogSession() {
|
||||
MutexLock lock(&mutex_);
|
||||
if (!CanRecordAnalyticsLocked("LogSession")) {
|
||||
@@ -668,7 +709,7 @@ AnalyticsRecorder::BuildConnectionAttemptMetadataParams(
|
||||
}
|
||||
|
||||
bool AnalyticsRecorder::CanRecordAnalyticsLocked(
|
||||
const std::string &method_name) {
|
||||
absl::string_view method_name) {
|
||||
NEARBY_LOGS(VERBOSE) << "AnalyticsRecorder LogEvent " << method_name
|
||||
<< " is calling.";
|
||||
if (event_logger_ == nullptr) {
|
||||
@@ -681,6 +722,7 @@ bool AnalyticsRecorder::CanRecordAnalyticsLocked(
|
||||
<< method_name << " after session has already been logged.";
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -697,6 +739,7 @@ void AnalyticsRecorder::LogClientSession() {
|
||||
<< connections_log.DebugString();
|
||||
|
||||
event_logger_->Log(connections_log);
|
||||
ResetClientSessionLoggingResouces();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -717,7 +760,7 @@ void AnalyticsRecorder::UpdateStrategySessionLocked(
|
||||
connections::Strategy strategy, SessionRole role) {
|
||||
// If we're not switching strategies, just update the current StrategySession
|
||||
// with the new role.
|
||||
if (strategy == current_strategy_) {
|
||||
if (strategy == current_strategy_ && current_strategy_session_ != nullptr) {
|
||||
if (absl::c_linear_search(current_strategy_session_->role(), role)) {
|
||||
// We've already acted as this role before, so make sure we've finished
|
||||
// recording the previous round.
|
||||
|
||||
@@ -164,11 +164,17 @@ class AnalyticsRecorder {
|
||||
// Error Code
|
||||
void OnErrorCode(const ErrorCodeParams ¶ms);
|
||||
|
||||
// Log the start client session event with start client session logging
|
||||
// resouces setup (e.g. client_session_, started_client_session_time_)
|
||||
void LogStartSession() ABSL_LOCKS_EXCLUDED(mutex_);
|
||||
|
||||
// Invokes event_logger_.Log() at the end of life of client. Log action is
|
||||
// called in a separate thread to allow synchronous potentially lengthy
|
||||
// execution.
|
||||
void LogSession() ABSL_LOCKS_EXCLUDED(mutex_);
|
||||
|
||||
bool IsSessionLogged();
|
||||
|
||||
private:
|
||||
// Tracks the chunks and duration of a Payload on a particular medium.
|
||||
class PendingPayload {
|
||||
@@ -267,7 +273,7 @@ class AnalyticsRecorder {
|
||||
outgoing_payloads_;
|
||||
};
|
||||
|
||||
bool CanRecordAnalyticsLocked(const std::string &method_name)
|
||||
bool CanRecordAnalyticsLocked(absl::string_view method_name)
|
||||
ABSL_SHARED_LOCKS_REQUIRED(mutex_);
|
||||
|
||||
// Callbacks the ConnectionsLog proto byte array data to the EventLogger with
|
||||
@@ -314,6 +320,10 @@ class AnalyticsRecorder {
|
||||
bool erase_item = true) ABSL_SHARED_LOCKS_REQUIRED(mutex_);
|
||||
void FinishStrategySessionLocked() ABSL_EXCLUSIVE_LOCKS_REQUIRED(mutex_);
|
||||
|
||||
// Reset the client cession's logging resources (e.g. current_strategy_,
|
||||
// current_advertising_phase_, current_discovery_phase_, etc)
|
||||
void ResetClientSessionLoggingResouces();
|
||||
|
||||
location::nearby::proto::connections::ConnectionsStrategy
|
||||
StrategyToConnectionStrategy(connections::Strategy strategy);
|
||||
location::nearby::proto::connections::PayloadType
|
||||
@@ -328,10 +338,10 @@ class AnalyticsRecorder {
|
||||
Mutex mutex_;
|
||||
|
||||
// ClientSession
|
||||
std::unique_ptr<proto::ConnectionsLog::ClientSession> client_session_ =
|
||||
std::make_unique<proto::ConnectionsLog::ClientSession>();
|
||||
std::unique_ptr<proto::ConnectionsLog::ClientSession> client_session_;
|
||||
absl::Time started_client_session_time_;
|
||||
bool session_was_logged_ ABSL_GUARDED_BY(mutex_) = false;
|
||||
bool start_client_session_was_logged_ ABSL_GUARDED_BY(mutex_) = false;
|
||||
|
||||
// Current StrategySession
|
||||
connections::Strategy current_strategy_ ABSL_GUARDED_BY(mutex_) =
|
||||
|
||||
@@ -55,6 +55,7 @@ using ::location::nearby::proto::connections::LOCAL_DISCONNECTION;
|
||||
using ::location::nearby::proto::connections::Medium;
|
||||
using ::location::nearby::proto::connections::RESULT_ERROR;
|
||||
using ::location::nearby::proto::connections::RESULT_SUCCESS;
|
||||
using ::location::nearby::proto::connections::START_CLIENT_SESSION;
|
||||
using ::location::nearby::proto::connections::START_STRATEGY_SESSION;
|
||||
using ::location::nearby::proto::connections::STOP_CLIENT_SESSION;
|
||||
using ::location::nearby::proto::connections::STOP_STRATEGY_SESSION;
|
||||
@@ -67,6 +68,7 @@ using ::location::nearby::proto::connections::WIFI_LAN_SOCKET_CREATION;
|
||||
using ::nearby::analytics::EventLogger;
|
||||
using ::testing::Contains;
|
||||
using ::protobuf_matchers::EqualsProto;
|
||||
using ::testing::Not;
|
||||
using ::testing::proto::Partially;
|
||||
|
||||
constexpr absl::Duration kDefaultTimeout = absl::Milliseconds(1000);
|
||||
@@ -76,6 +78,12 @@ class FakeEventLogger : public EventLogger {
|
||||
explicit FakeEventLogger(CountDownLatch& client_session_done_latch)
|
||||
: client_session_done_latch_(client_session_done_latch) {}
|
||||
|
||||
FakeEventLogger(CountDownLatch& client_session_done_latch,
|
||||
CountDownLatch* start_client_session_done_latch_ptr)
|
||||
: client_session_done_latch_(client_session_done_latch),
|
||||
start_client_session_done_latch_ptr_(
|
||||
start_client_session_done_latch_ptr) {}
|
||||
|
||||
void Log(const ::google::protobuf::MessageLite& message) override {
|
||||
auto connections_log = dynamic_cast<const proto::ConnectionsLog*>(&message);
|
||||
if (connections_log == nullptr) {
|
||||
@@ -94,6 +102,10 @@ class FakeEventLogger : public EventLogger {
|
||||
if (event_type == STOP_CLIENT_SESSION) {
|
||||
client_session_done_latch_.CountDown();
|
||||
}
|
||||
if (start_client_session_done_latch_ptr_ != nullptr &&
|
||||
event_type == START_CLIENT_SESSION) {
|
||||
start_client_session_done_latch_ptr_->CountDown();
|
||||
}
|
||||
}
|
||||
|
||||
int GetLoggedClientSessionCount() const {
|
||||
@@ -108,14 +120,27 @@ class FakeEventLogger : public EventLogger {
|
||||
|
||||
std::vector<EventType> GetLoggedEventTypes() { return logged_event_types_; }
|
||||
|
||||
void SetClientSessionDoneLatch(
|
||||
const CountDownLatch& client_session_done_latch) {
|
||||
client_session_done_latch_ = client_session_done_latch;
|
||||
}
|
||||
|
||||
void SetStartClientSessionDoneLatchPtr(
|
||||
CountDownLatch* start_client_session_done_latch_ptr) {
|
||||
start_client_session_done_latch_ptr_ = start_client_session_done_latch_ptr;
|
||||
}
|
||||
|
||||
private:
|
||||
int logged_client_session_count_ = 0;
|
||||
CountDownLatch& client_session_done_latch_;
|
||||
CountDownLatch* start_client_session_done_latch_ptr_ = nullptr;
|
||||
ConnectionsLog::ClientSession logged_client_session_;
|
||||
ConnectionsLog::ErrorCode error_code_;
|
||||
std::vector<EventType> logged_event_types_;
|
||||
};
|
||||
|
||||
// Test if session_was_logged_ is reset by checking if LogSession can take
|
||||
// effect again or not.
|
||||
TEST(AnalyticsRecorderTest, SessionOnlyLoggedOnceWorks) {
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
@@ -941,6 +966,777 @@ TEST(AnalyticsRecorderTest, SetErrorCodeFieldsCorrectlyForCommonError) {
|
||||
)pb")));
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest, CheckIfSessionWasLogged) {
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
// LogSession to count down client_session_done_latch.
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_TRUE(analytics_recorder.IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest, ConstructAnalyticsRecorder) {
|
||||
CountDownLatch client_session_done_latch(0);
|
||||
CountDownLatch start_client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch,
|
||||
&start_client_session_done_latch);
|
||||
|
||||
// Call the constructor to count down the session_done_latch.
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
ASSERT_TRUE(start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
std::vector<EventType> event_types = event_logger.GetLoggedEventTypes();
|
||||
EXPECT_EQ(event_types.size(), 1);
|
||||
EXPECT_THAT(event_types, Contains(START_CLIENT_SESSION).Times(1));
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest,
|
||||
StartClientSessionOnlyLoggedOnceWorksAfterAnalyticsRecorderIsConstructed) {
|
||||
CountDownLatch client_session_done_latch(0);
|
||||
CountDownLatch start_client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch,
|
||||
&start_client_session_done_latch);
|
||||
|
||||
// Call the constructor to count down the start_client_session_done_latch.
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
ASSERT_TRUE(start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// Log start client session once.
|
||||
EXPECT_THAT(event_logger.GetLoggedEventTypes(),
|
||||
Contains(START_CLIENT_SESSION).Times(1));
|
||||
|
||||
// Reset the start_client_session_done_latch. However, LogStartSession cannot
|
||||
// count down the start_client_session_done_latch.
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_FALSE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// No more start client session was logged.
|
||||
EXPECT_THAT(event_logger.GetLoggedEventTypes(),
|
||||
Contains(START_CLIENT_SESSION).Times(1));
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest,
|
||||
CanLogStartClientSessionOnceAgainAfterSessionWasLogged) {
|
||||
CountDownLatch client_session_done_latch(0);
|
||||
CountDownLatch start_client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch,
|
||||
&start_client_session_done_latch);
|
||||
|
||||
// Call the constructor to count down the start_client_session_done_latch.
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
ASSERT_TRUE(start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// Log start client session once.
|
||||
EXPECT_THAT(event_logger.GetLoggedEventTypes(),
|
||||
Contains(START_CLIENT_SESSION).Times(1));
|
||||
|
||||
// Reset the client_session_done_latch. Call LogSession to count down the
|
||||
// client_session_done_latch.
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// Reset the start_client_session_done_latch. Call LogStartSession to count
|
||||
// down the start_client_session_done_latch.
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
analytics_recorder.LogStartSession();
|
||||
analytics_recorder.LogStartSession();
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// Can log start client session once again.
|
||||
EXPECT_THAT(event_logger.GetLoggedEventTypes(),
|
||||
Contains(START_CLIENT_SESSION).Times(2));
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest,
|
||||
ClearcIncomingConnectionRequestsAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
std::vector<Medium> mediums = {BLE, BLUETOOTH};
|
||||
std::string endpoint_id_0 = "endpoint_id_0";
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
analytics_recorder.OnStartAdvertising(strategy, mediums);
|
||||
analytics_recorder.OnConnectionRequestReceived(endpoint_id_0);
|
||||
analytics_recorder.OnLocalEndpointAccepted(endpoint_id_0);
|
||||
analytics_recorder.OnRemoteEndpointAccepted(endpoint_id_0);
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession(); // call ResetClientSessionLoggingResouces
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(), Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
received_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
>
|
||||
>)pb")));
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
std::string endpoint_id_1 = "endpoint_id_1";
|
||||
analytics_recorder.OnConnectionRequestReceived(endpoint_id_1);
|
||||
analytics_recorder.OnLocalEndpointAccepted(endpoint_id_1);
|
||||
analytics_recorder.OnRemoteEndpointAccepted(endpoint_id_1);
|
||||
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(new_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// - if the current_strategy_session_ and current_advertising_phase_ are not
|
||||
// reset, the duplicate advertising_phase (with the additional
|
||||
// received_connection_request) will append to the strategy_session)
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Not(Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
received_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
>
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
received_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
received_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
>
|
||||
>)pb"))));
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest,
|
||||
ClearcOutgoingConnectionRequestsAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
std::vector<Medium> mediums = {BLE, BLUETOOTH};
|
||||
std::string endpoint_id_0 = "endpoint_id_0";
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
analytics_recorder.OnStartDiscovery(strategy, mediums);
|
||||
|
||||
analytics_recorder.OnConnectionRequestSent(endpoint_id_0);
|
||||
analytics_recorder.OnLocalEndpointAccepted(endpoint_id_0);
|
||||
analytics_recorder.OnRemoteEndpointAccepted(endpoint_id_0);
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession(); // call ResetClientSessionLoggingResouces
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(), Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: DISCOVERER
|
||||
discovery_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
discovery_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
sent_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
>
|
||||
>)pb")));
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
std::string endpoint_id_1 = "endpoint_id_1";
|
||||
analytics_recorder.OnConnectionRequestSent(endpoint_id_1);
|
||||
analytics_recorder.OnLocalEndpointAccepted(endpoint_id_1);
|
||||
analytics_recorder.OnRemoteEndpointAccepted(endpoint_id_1);
|
||||
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// - if the current_strategy_session_ and current_discovery_phase_ are
|
||||
// not reset, the duplicate discovery_phase (with the additional
|
||||
// sent_connection_request) will append to the strategy_session)
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Not(Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: DISCOVERER
|
||||
discovery_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
discovery_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
sent_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
>
|
||||
discovery_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
discovery_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
sent_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
sent_connection_request <
|
||||
local_response: ACCEPTED
|
||||
remote_response: ACCEPTED
|
||||
>
|
||||
>
|
||||
>)pb"))));
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest, ClearcActiveConnectionsAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
std::vector<Medium> mediums = {BLE, BLUETOOTH};
|
||||
std::string endpoint_id = "endpoint_id";
|
||||
std::string connection_token = "connection_token";
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
analytics_recorder.OnStartAdvertising(strategy, mediums);
|
||||
|
||||
analytics_recorder.OnConnectionEstablished(endpoint_id, BLUETOOTH,
|
||||
connection_token);
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession(); // call ResetClientSessionLoggingResouces
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(), Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
established_connection <
|
||||
medium: BLUETOOTH
|
||||
disconnection_reason: UNFINISHED
|
||||
connection_token: "connection_token"
|
||||
>
|
||||
>)pb")));
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// - if the current_strategy_session_ and advertising_phase_ are not
|
||||
// reset, the duplicate advertising_phase_ (with the additional
|
||||
// will append to the strategy_session), and the active connection (i.e.
|
||||
// established_connection) will stay there.
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Not(Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
established_connection <
|
||||
medium: BLUETOOTH
|
||||
disconnection_reason: UNFINISHED
|
||||
connection_token: "connection_token"
|
||||
>
|
||||
>)pb"))));
|
||||
}
|
||||
|
||||
TEST(AnalyticsRecorderTest,
|
||||
ClearBandwidthUpgradeAttemptsAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
std::vector<Medium> mediums = {BLE, BLUETOOTH};
|
||||
std::string endpoint_id = "endpoint_id";
|
||||
std::string endpoint_id_1 = "endpoint_id_1";
|
||||
std::string endpoint_id_2 = "endpoint_id_2";
|
||||
std::string connection_token = "connection_token";
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
analytics_recorder.OnStartAdvertising(strategy, mediums);
|
||||
|
||||
analytics_recorder.OnBandwidthUpgradeStarted(endpoint_id, BLE, WIFI_LAN,
|
||||
INCOMING, connection_token);
|
||||
|
||||
analytics_recorder.OnBandwidthUpgradeStarted(
|
||||
endpoint_id_1, BLUETOOTH, WIFI_LAN, INCOMING, connection_token);
|
||||
// - Error to upgrade.
|
||||
analytics_recorder.OnBandwidthUpgradeError(endpoint_id, WIFI_LAN_MEDIUM_ERROR,
|
||||
WIFI_LAN_SOCKET_CREATION);
|
||||
// - Success to upgrade.
|
||||
analytics_recorder.OnBandwidthUpgradeSuccess(endpoint_id_1);
|
||||
|
||||
// - Upgrade is unfinished.
|
||||
analytics_recorder.OnBandwidthUpgradeStarted(
|
||||
endpoint_id_2, BLUETOOTH, WIFI_LAN, INCOMING, connection_token);
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession(); // call ResetClientSessionLoggingResouces
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// - if the current_strategy_session_ and advertising_phase_ are not
|
||||
// reset, the duplicate advertising_phase_, and the upgrade_attempts (i.e.
|
||||
// bandwidth_upgrade_attempts_) will stay there.
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(), Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
upgrade_attempt <
|
||||
direction: INCOMING
|
||||
from_medium: BLE
|
||||
to_medium: WIFI_LAN
|
||||
upgrade_result: WIFI_LAN_MEDIUM_ERROR
|
||||
error_stage: WIFI_LAN_SOCKET_CREATION
|
||||
connection_token: "connection_token"
|
||||
>
|
||||
upgrade_attempt <
|
||||
direction: INCOMING
|
||||
from_medium: BLUETOOTH
|
||||
to_medium: WIFI_LAN
|
||||
upgrade_result: UPGRADE_RESULT_SUCCESS
|
||||
error_stage: UPGRADE_SUCCESS
|
||||
connection_token: "connection_token"
|
||||
>
|
||||
upgrade_attempt {
|
||||
direction: INCOMING
|
||||
from_medium: BLUETOOTH
|
||||
to_medium: WIFI_LAN
|
||||
upgrade_result: UNFINISHED_ERROR
|
||||
error_stage: UPGRADE_UNFINISHED
|
||||
connection_token: "connection_token"
|
||||
}
|
||||
>)pb")));
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Not(Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
upgrade_attempt <
|
||||
direction: INCOMING
|
||||
from_medium: BLE
|
||||
to_medium: WIFI_LAN
|
||||
upgrade_result: WIFI_LAN_MEDIUM_ERROR
|
||||
error_stage: WIFI_LAN_SOCKET_CREATION
|
||||
connection_token: "connection_token"
|
||||
>
|
||||
upgrade_attempt <
|
||||
direction: INCOMING
|
||||
from_medium: BLUETOOTH
|
||||
to_medium: WIFI_LAN
|
||||
upgrade_result: UPGRADE_RESULT_SUCCESS
|
||||
error_stage: UPGRADE_SUCCESS
|
||||
connection_token: "connection_token"
|
||||
>
|
||||
upgrade_attempt {
|
||||
direction: INCOMING
|
||||
from_medium: BLUETOOTH
|
||||
to_medium: WIFI_LAN
|
||||
upgrade_result: UNFINISHED_ERROR
|
||||
error_stage: UPGRADE_UNFINISHED
|
||||
connection_token: "connection_token"
|
||||
}
|
||||
>)pb"))));
|
||||
}
|
||||
|
||||
// Test if current_strategy_ is reset by checking if the same strategy would
|
||||
// be logged for different client sessions or not. If yes, it should be logged.
|
||||
// Otherwise, not.
|
||||
TEST(AnalyticsRecorderTest,
|
||||
CanLogSeparateStartStrategySessionForSameStrategyAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
analytics_recorder.OnStartAdvertising(strategy, {BLUETOOTH});
|
||||
analytics_recorder.OnStopAdvertising();
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedEventTypes(),
|
||||
Contains(START_STRATEGY_SESSION)
|
||||
.Times(1)); // the same strategy session shouldn't be logged
|
||||
// again with the same client sesssion.
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
analytics_recorder.OnStartAdvertising(strategy, {BLUETOOTH});
|
||||
analytics_recorder.OnStopAdvertising();
|
||||
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(new_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedEventTypes(),
|
||||
Contains(START_STRATEGY_SESSION).Times(2));
|
||||
}
|
||||
|
||||
// Test if current_strategy_session_ is reset. If not, the same strategy session
|
||||
// proto will be logged.
|
||||
TEST(AnalyticsRecorderTest,
|
||||
NotLogSameStrategySessionProtoAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
std::vector<Medium> mediums = {BLE, BLUETOOTH};
|
||||
std::string endpoint_id = "endpoint_id";
|
||||
std::string connection_token = "";
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder{&event_logger};
|
||||
|
||||
analytics_recorder.OnStartAdvertising(
|
||||
strategy, mediums); // via OnStartAdvertising, current_strategy_session_
|
||||
// is set in UpdateStrategySessionLocked.
|
||||
analytics_recorder.OnStopAdvertising();
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
std::string strategy_session_proto = R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLE
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
>)pb";
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Partially(EqualsProto(strategy_session_proto)));
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
// - if current_strategy_session_ is reset, the same strategy_session_proto
|
||||
// will be logged.
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(new_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Not(Partially(EqualsProto(strategy_session_proto))));
|
||||
}
|
||||
|
||||
// Test if current_advertising_phase_ is reset.
|
||||
TEST(AnalyticsRecorderTest,
|
||||
NotLogDuplicateAdvertisingPhaseAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
analytics_recorder.OnStartAdvertising(
|
||||
strategy, {BLUETOOTH}); // set current_advertising_phase_
|
||||
analytics_recorder.OnStopAdvertising();
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(), Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
>)pb")));
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
// - if the current_strategy_session_ and current_advertising_phase_ are
|
||||
// not reset, the same strategy_session with two same advertising_phase will
|
||||
// be logged.
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Not(Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: ADVERTISER
|
||||
advertising_phase <
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
advertising_phase <
|
||||
medium: BLUETOOTH
|
||||
advertising_metadata <
|
||||
supports_extended_ble_advertisements: false
|
||||
connected_ap_frequency: 0
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
>)pb"))));
|
||||
}
|
||||
|
||||
// Test if current_discovery_phase_ is reset.
|
||||
TEST(AnalyticsRecorderTest,
|
||||
NotLogDuplicateDiscoveryPhaseAfterSessionWasLogged) {
|
||||
connections::Strategy strategy = connections::Strategy::kP2pStar;
|
||||
|
||||
CountDownLatch client_session_done_latch(1);
|
||||
FakeEventLogger event_logger(client_session_done_latch);
|
||||
AnalyticsRecorder analytics_recorder(&event_logger);
|
||||
|
||||
analytics_recorder.OnStartDiscovery(
|
||||
strategy, {BLUETOOTH}, /*is_extended_advertisement_supported=*/true,
|
||||
/*connected_ap_frequency=*/1,
|
||||
/*is_nfc_available=*/false); // set current_discovery_phase_
|
||||
analytics_recorder.OnStopDiscovery();
|
||||
analytics_recorder.OnEndpointFound(BLUETOOTH);
|
||||
|
||||
// LogSession
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(), Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: DISCOVERER
|
||||
discovery_phase <
|
||||
medium: BLUETOOTH
|
||||
discovery_metadata <
|
||||
supports_extended_ble_advertisements: true
|
||||
connected_ap_frequency: 1
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
>)pb")));
|
||||
|
||||
// LogStartSession
|
||||
CountDownLatch new_start_client_session_done_latch(1);
|
||||
event_logger.SetStartClientSessionDoneLatchPtr(
|
||||
&new_start_client_session_done_latch);
|
||||
analytics_recorder.LogStartSession();
|
||||
ASSERT_TRUE(
|
||||
new_start_client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
// LogSession again
|
||||
// - if the current_strategy_session_ and current_discovery_phase_ are not
|
||||
// reset, the same strategy_session with two same discovery_phase will be
|
||||
// logged.
|
||||
CountDownLatch new_client_session_done_latch(1);
|
||||
event_logger.SetClientSessionDoneLatch(new_client_session_done_latch);
|
||||
analytics_recorder.LogSession();
|
||||
ASSERT_TRUE(client_session_done_latch.Await(kDefaultTimeout).result());
|
||||
|
||||
EXPECT_THAT(event_logger.GetLoggedClientSession(),
|
||||
Not(Partially(EqualsProto(R"pb(
|
||||
strategy_session <
|
||||
strategy: P2P_STAR
|
||||
role: DISCOVERER
|
||||
discovery_phase <
|
||||
medium: BLUETOOTH
|
||||
discovery_metadata <
|
||||
supports_extended_ble_advertisements: true
|
||||
connected_ap_frequency: 1
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
discovery_phase <
|
||||
medium: BLUETOOTH
|
||||
discovery_metadata <
|
||||
supports_extended_ble_advertisements: true
|
||||
connected_ap_frequency: 1
|
||||
supports_nfc_technology: false
|
||||
>
|
||||
>
|
||||
>)pb"))));
|
||||
}
|
||||
|
||||
} // namespace
|
||||
} // namespace analytics
|
||||
} // namespace nearby
|
||||
|
||||
@@ -17,10 +17,12 @@
|
||||
#include <cstdlib>
|
||||
#include <functional>
|
||||
#include <limits>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <utility>
|
||||
|
||||
#include "internal/analytics/event_logger.h"
|
||||
#include "absl/container/flat_hash_map.h"
|
||||
#include "absl/container/flat_hash_set.h"
|
||||
#include "absl/strings/escaping.h"
|
||||
@@ -104,7 +106,6 @@ void ClientProxy::Reset() {
|
||||
StoppedDiscovery();
|
||||
RemoveAllEndpoints();
|
||||
ExitHighVisibilityMode();
|
||||
analytics_recorder_->LogSession();
|
||||
}
|
||||
|
||||
void ClientProxy::StartedAdvertising(
|
||||
@@ -143,7 +144,7 @@ void ClientProxy::StoppedAdvertising() {
|
||||
analytics_recorder_->OnStopAdvertising();
|
||||
}
|
||||
// advertising_options_ is purposefully not cleared here.
|
||||
ResetLocalEndpointIdIfNeeded();
|
||||
OnSessionComplete();
|
||||
|
||||
ExitHighVisibilityMode();
|
||||
}
|
||||
@@ -182,7 +183,7 @@ void ClientProxy::StoppedDiscovery() {
|
||||
analytics_recorder_->OnStopDiscovery();
|
||||
}
|
||||
// discovery_options_ is purposefully not cleared here.
|
||||
ResetLocalEndpointIdIfNeeded();
|
||||
OnSessionComplete();
|
||||
}
|
||||
|
||||
bool ClientProxy::IsDiscoveringServiceId(const std::string& service_id) const {
|
||||
@@ -357,7 +358,7 @@ void ClientProxy::OnDisconnected(const std::string& endpoint_id, bool notify) {
|
||||
item->connection_listener.disconnected_cb({endpoint_id});
|
||||
}
|
||||
connections_.erase(endpoint_id);
|
||||
ResetLocalEndpointIdIfNeeded();
|
||||
OnSessionComplete();
|
||||
}
|
||||
|
||||
CancelEndpoint(endpoint_id);
|
||||
@@ -657,13 +658,16 @@ void ClientProxy::RemoveAllEndpoints() {
|
||||
// just remove without notifying.
|
||||
connections_.clear();
|
||||
cancellation_flags_.clear();
|
||||
local_endpoint_id_.clear();
|
||||
OnSessionComplete();
|
||||
}
|
||||
|
||||
void ClientProxy::ResetLocalEndpointIdIfNeeded() {
|
||||
void ClientProxy::OnSessionComplete() {
|
||||
MutexLock lock(&mutex_);
|
||||
if (connections_.empty() && !IsAdvertising() && !IsDiscovering()) {
|
||||
local_endpoint_id_.clear();
|
||||
|
||||
analytics_recorder_->LogSession();
|
||||
analytics_recorder_->LogStartSession();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -236,7 +236,7 @@ class ClientProxy final {
|
||||
};
|
||||
|
||||
void RemoveAllEndpoints();
|
||||
void ResetLocalEndpointIdIfNeeded();
|
||||
void OnSessionComplete();
|
||||
bool ConnectionStatusesContains(const std::string& endpoint_id,
|
||||
Connection::Status status_to_match) const;
|
||||
void AppendConnectionStatus(const std::string& endpoint_id,
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
#include "absl/types/span.h"
|
||||
#include "connections/listeners.h"
|
||||
#include "connections/strategy.h"
|
||||
#include "internal/analytics/event_logger.h"
|
||||
#include "internal/platform/byte_array.h"
|
||||
#include "internal/platform/feature_flags.h"
|
||||
#include "internal/platform/medium_environment.h"
|
||||
@@ -48,6 +49,13 @@ constexpr FeatureFlags::Flags kTestCases[] = {
|
||||
},
|
||||
};
|
||||
|
||||
class FakeEventLogger : public ::nearby::analytics::EventLogger {
|
||||
public:
|
||||
explicit FakeEventLogger() = default;
|
||||
|
||||
void Log(const ::google::protobuf::MessageLite& message) override {}
|
||||
};
|
||||
|
||||
class ClientProxyTest : public ::testing::TestWithParam<FeatureFlags::Flags> {
|
||||
protected:
|
||||
struct MockDiscoveryListener {
|
||||
@@ -107,7 +115,23 @@ class ClientProxyTest : public ::testing::TestWithParam<FeatureFlags::Flags> {
|
||||
return endpoint;
|
||||
}
|
||||
|
||||
void StopAdvertising(ClientProxy* client) { client->StoppedAdvertising(); }
|
||||
void StopAdvertising(ClientProxy* client) {
|
||||
client->StoppedAdvertising();
|
||||
EXPECT_FALSE(client->IsAdvertising());
|
||||
}
|
||||
|
||||
void OnAdvertisingConnectionInitiated(ClientProxy* client,
|
||||
const Endpoint& endpoint) {
|
||||
EXPECT_CALL(mock_advertising_connection_.initiated_cb, Call).Times(1);
|
||||
const std::string auth_token{"auth_token"};
|
||||
const ByteArray raw_auth_token{auth_token};
|
||||
const std::string connection_token{"conntokn"};
|
||||
discovery_connection_info_.remote_endpoint_info = endpoint.info;
|
||||
client->OnConnectionInitiated(
|
||||
endpoint.id, discovery_connection_info_, connection_options_,
|
||||
advertising_connection_listener_, connection_token);
|
||||
EXPECT_TRUE(client->HasPendingConnectionToEndpoint(endpoint.id));
|
||||
}
|
||||
|
||||
Endpoint StartDiscovery(ClientProxy* client, DiscoveryListener listener) {
|
||||
Endpoint endpoint{
|
||||
@@ -119,6 +143,11 @@ class ClientProxyTest : public ::testing::TestWithParam<FeatureFlags::Flags> {
|
||||
return endpoint;
|
||||
}
|
||||
|
||||
void StopDiscovery(ClientProxy* client) {
|
||||
client->StoppedDiscovery();
|
||||
EXPECT_FALSE(client->IsDiscovering());
|
||||
}
|
||||
|
||||
void OnDiscoveryEndpointFound(ClientProxy* client, const Endpoint& endpoint) {
|
||||
EXPECT_CALL(mock_discovery_.endpoint_found_cb, Call).Times(1);
|
||||
client->OnEndpointFound(service_id_, endpoint.id, endpoint.info, medium_);
|
||||
@@ -214,6 +243,8 @@ class ClientProxyTest : public ::testing::TestWithParam<FeatureFlags::Flags> {
|
||||
client->OnPayloadProgress(endpoint.id, {});
|
||||
}
|
||||
|
||||
MockConnectionListener mock_advertising_connection_;
|
||||
|
||||
MockDiscoveryListener mock_discovery_;
|
||||
MockConnectionListener mock_discovery_connection_;
|
||||
MockPayloadListener mock_discovery_payload_;
|
||||
@@ -224,8 +255,10 @@ class ClientProxyTest : public ::testing::TestWithParam<FeatureFlags::Flags> {
|
||||
};
|
||||
Strategy strategy_{Strategy::kP2pPointToPoint};
|
||||
const std::string service_id_{"service"};
|
||||
ClientProxy client1_;
|
||||
ClientProxy client2_;
|
||||
FakeEventLogger event_logger1_;
|
||||
FakeEventLogger event_logger2_;
|
||||
ClientProxy client1_{&event_logger1_};
|
||||
ClientProxy client2_{&event_logger2_};
|
||||
std::string auth_token_ = "auth_token";
|
||||
ByteArray raw_auth_token_ = ByteArray(auth_token_);
|
||||
ByteArray payload_bytes_{"bytes"};
|
||||
@@ -234,7 +267,14 @@ class ClientProxyTest : public ::testing::TestWithParam<FeatureFlags::Flags> {
|
||||
.raw_authentication_token = raw_auth_token_,
|
||||
.is_incoming_connection = true,
|
||||
};
|
||||
ConnectionListener advertising_connection_listener_;
|
||||
ConnectionListener advertising_connection_listener_{
|
||||
.initiated_cb = mock_advertising_connection_.initiated_cb.AsStdFunction(),
|
||||
};
|
||||
ConnectionResponseInfo discovery_connection_info_{
|
||||
.authentication_token = auth_token_,
|
||||
.raw_authentication_token = raw_auth_token_,
|
||||
.is_incoming_connection = false,
|
||||
};
|
||||
ConnectionListener discovery_connection_listener_{
|
||||
.initiated_cb = mock_discovery_connection_.initiated_cb.AsStdFunction(),
|
||||
.accepted_cb = mock_discovery_connection_.accepted_cb.AsStdFunction(),
|
||||
@@ -686,6 +726,177 @@ TEST_F(ClientProxyTest, EndpointIdRotateWhenLowVizAdvertisementWithLowPower) {
|
||||
EXPECT_NE(advertising_endpoint_1.id, advertising_endpoint_2.id);
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest, NotLogSessionForStoppedAdvertisingWithConnection) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
OnAdvertisingConnectionInitiated(&client1_, advertising_endpoint);
|
||||
|
||||
StartDiscovery(&client2_, discovery_listener_);
|
||||
OnDiscoveryEndpointFound(&client2_, advertising_endpoint);
|
||||
OnDiscoveryConnectionInitiated(&client2_, advertising_endpoint);
|
||||
|
||||
// Before
|
||||
EXPECT_TRUE(client1_.HasPendingConnectionToEndpoint(
|
||||
advertising_endpoint.id)); // Connections are available
|
||||
EXPECT_FALSE(client1_.IsDiscovering()); // No Discovery
|
||||
EXPECT_TRUE(client1_.IsAdvertising()); // Advertising
|
||||
EXPECT_FALSE(client1_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
|
||||
// After
|
||||
StopAdvertising(&client1_); // No Advertising
|
||||
EXPECT_FALSE(client1_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest,
|
||||
LogSessionForStoppedAdvertisingWhenNoConnectionsAndNoDiscovering) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
|
||||
// Before
|
||||
EXPECT_FALSE(client1_.HasPendingConnectionToEndpoint(
|
||||
advertising_endpoint.id)); // No Connections
|
||||
EXPECT_FALSE(client1_.IsDiscovering()); // No Discovery
|
||||
EXPECT_TRUE(client1_.IsAdvertising()); // Advertising
|
||||
EXPECT_FALSE(client1_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
|
||||
// After
|
||||
StopAdvertising(&client1_);
|
||||
EXPECT_TRUE(client1_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest, NotLogSessionForStoppedDiscoveryWithConnection) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
|
||||
StartDiscovery(&client2_, discovery_listener_);
|
||||
OnDiscoveryEndpointFound(&client2_, advertising_endpoint);
|
||||
|
||||
// Before
|
||||
OnDiscoveryConnectionInitiated(
|
||||
&client2_, advertising_endpoint); // Connections are available
|
||||
EXPECT_FALSE(client2_.IsAdvertising()); // No Advertising
|
||||
EXPECT_TRUE(client2_.IsDiscovering()); // Discovering
|
||||
EXPECT_FALSE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
|
||||
// After
|
||||
StopDiscovery(&client2_);
|
||||
EXPECT_FALSE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest,
|
||||
NotLogSessionForStoppedDiscoveryWithoutConnectionsAndAdvertising) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
|
||||
StartDiscovery(&client2_, discovery_listener_);
|
||||
|
||||
// Before
|
||||
EXPECT_FALSE(client2_.IsAdvertising()); // No Advertising
|
||||
EXPECT_TRUE(client2_.IsDiscovering()); // Discoverying
|
||||
EXPECT_FALSE(client2_.HasPendingConnectionToEndpoint(
|
||||
advertising_endpoint.id)); // No Connections
|
||||
|
||||
// After
|
||||
StopDiscovery(&client2_);
|
||||
EXPECT_TRUE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest, LogSessionOnDisconnectedWithOneConnection) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
StartDiscovery(&client2_, discovery_listener_);
|
||||
OnDiscoveryEndpointFound(&client2_, advertising_endpoint);
|
||||
OnDiscoveryConnectionInitiated(&client2_, advertising_endpoint);
|
||||
|
||||
// Before
|
||||
EXPECT_FALSE(client2_.IsAdvertising()); // No Advertising
|
||||
StopDiscovery(&client2_); // No Discovery
|
||||
EXPECT_TRUE(client2_.HasPendingConnectionToEndpoint(
|
||||
advertising_endpoint.id)); // One Connection
|
||||
|
||||
// After
|
||||
OnDiscoveryConnectionDisconnected(&client2_, advertising_endpoint);
|
||||
EXPECT_TRUE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest,
|
||||
NotLogSessionOnDisconnectedWithoutConnectionsDiscoveringAdvertising) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
|
||||
// Before
|
||||
EXPECT_FALSE(client2_.IsAdvertising()); // No Advertising
|
||||
EXPECT_FALSE(client2_.IsDiscovering()); // No Discovery
|
||||
EXPECT_FALSE(client2_.HasPendingConnectionToEndpoint(
|
||||
advertising_endpoint.id)); // No Connections
|
||||
|
||||
// After
|
||||
client2_.OnDisconnected(advertising_endpoint.id, /*notify=*/false);
|
||||
EXPECT_FALSE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest, NotLogSessionOnDisconnectedWhenMoreThanOneConnection) {
|
||||
ClientProxy client3;
|
||||
Endpoint advertising_endpoint_1 =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
Endpoint advertising_endpoint_2 =
|
||||
StartAdvertising(&client2_, advertising_connection_listener_);
|
||||
StartDiscovery(&client3, discovery_listener_);
|
||||
|
||||
OnDiscoveryEndpointFound(&client3, advertising_endpoint_1);
|
||||
OnDiscoveryConnectionInitiated(&client3, advertising_endpoint_1);
|
||||
OnDiscoveryEndpointFound(&client3, advertising_endpoint_2);
|
||||
OnDiscoveryConnectionInitiated(&client3, advertising_endpoint_2);
|
||||
|
||||
// Before
|
||||
// - More than one Connection
|
||||
EXPECT_TRUE(
|
||||
client3.HasPendingConnectionToEndpoint(advertising_endpoint_1.id));
|
||||
EXPECT_TRUE(
|
||||
client3.HasPendingConnectionToEndpoint(advertising_endpoint_2.id));
|
||||
EXPECT_FALSE(client3.IsAdvertising()); // No Advertising
|
||||
StopDiscovery(&client3); // No Discovery
|
||||
|
||||
// After
|
||||
client2_.OnDisconnected(advertising_endpoint_1.id, /*notify=*/false);
|
||||
EXPECT_FALSE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest,
|
||||
NotLogSessionOnDisconnectedForDiscoveringWithOnlyOneConnection) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
StartDiscovery(&client2_, discovery_listener_);
|
||||
OnDiscoveryEndpointFound(&client2_, advertising_endpoint);
|
||||
OnDiscoveryConnectionInitiated(&client2_, advertising_endpoint);
|
||||
|
||||
// Before
|
||||
EXPECT_FALSE(client2_.IsAdvertising()); // No Advertising
|
||||
EXPECT_TRUE(client2_.IsDiscovering()); // Discovering
|
||||
EXPECT_TRUE(client2_.HasPendingConnectionToEndpoint(
|
||||
advertising_endpoint.id)); // One Connection
|
||||
|
||||
// After
|
||||
OnDiscoveryConnectionDisconnected(&client2_, advertising_endpoint);
|
||||
EXPECT_FALSE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
TEST_F(ClientProxyTest, LogSessionForResetClientProxy) {
|
||||
Endpoint advertising_endpoint =
|
||||
StartAdvertising(&client1_, advertising_connection_listener_);
|
||||
StartDiscovery(&client2_, discovery_listener_);
|
||||
OnDiscoveryEndpointFound(&client2_, advertising_endpoint);
|
||||
OnDiscoveryConnectionInitiated(&client2_, advertising_endpoint);
|
||||
|
||||
EXPECT_FALSE(client1_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
client1_.Reset();
|
||||
EXPECT_TRUE(client1_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
|
||||
EXPECT_FALSE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
client2_.Reset();
|
||||
EXPECT_TRUE(client2_.GetAnalyticsRecorder().IsSessionLogged());
|
||||
}
|
||||
|
||||
} // namespace
|
||||
} // namespace connections
|
||||
} // namespace nearby
|
||||
|
||||
Reference in New Issue
Block a user