Report service info callback metrics data

Bug: 287546772
Test: atest FrameworksNetTestCases
Change-Id: I630c0e4921f7acf42bf29812d9790ee5a894d60b
This commit is contained in:
Paul Hu
2023-08-01 10:26:49 +08:00
parent 6014905672
commit ddce5919af
4 changed files with 163 additions and 10 deletions

View File

@@ -221,4 +221,52 @@ public class NetworkNsdReportedMetrics {
builder.setEventDurationMillisec(durationMs); builder.setEventDurationMillisec(durationMs);
mDependencies.statsWrite(builder.build()); mDependencies.statsWrite(builder.build());
} }
/**
* Report service info callback registered metric data.
*
* @param transactionId The transaction id of service info callback registration.
*/
public void reportServiceInfoCallbackRegistered(int transactionId) {
final Builder builder = makeReportedBuilder();
builder.setTransactionId(transactionId);
builder.setType(NsdEventType.NET_SERVICE_INFO_CALLBACK);
builder.setQueryResult(MdnsQueryResult.MQR_SERVICE_INFO_CALLBACK_REGISTERED);
mDependencies.statsWrite(builder.build());
}
/**
* Report service info callback registration failed metric data.
*
* @param transactionId The transaction id of service callback registration.
*/
public void reportServiceInfoCallbackRegistrationFailed(int transactionId) {
final Builder builder = makeReportedBuilder();
builder.setTransactionId(transactionId);
builder.setType(NsdEventType.NET_SERVICE_INFO_CALLBACK);
builder.setQueryResult(MdnsQueryResult.MQR_SERVICE_INFO_CALLBACK_REGISTRATION_FAILED);
mDependencies.statsWrite(builder.build());
}
/**
* Report service callback unregistered metric data.
*
* @param transactionId The transaction id of service callback registration.
* @param durationMs The duration of service callback stayed registered.
* @param updateCallbackCount The count of service update callbacks during this registration.
* @param lostCallbackCount The count of service lost callbacks during this registration.
* @param isServiceFromCache Whether the resolved service is from cache.
*/
public void reportServiceInfoCallbackUnregistered(int transactionId, long durationMs,
int updateCallbackCount, int lostCallbackCount, boolean isServiceFromCache) {
final Builder builder = makeReportedBuilder();
builder.setTransactionId(transactionId);
builder.setType(NsdEventType.NET_SERVICE_INFO_CALLBACK);
builder.setQueryResult(MdnsQueryResult.MQR_SERVICE_INFO_CALLBACK_UNREGISTERED);
builder.setEventDurationMillisec(durationMs);
builder.setFoundCallbackCount(updateCallbackCount);
builder.setLostCallbackCount(lostCallbackCount);
builder.setIsKnownService(isServiceFromCache);
mDependencies.statsWrite(builder.build());
}
} }

View File

@@ -1114,6 +1114,7 @@ public class NsdService extends INsdManager.Stub {
resolveServiceType, listener, options); resolveServiceType, listener, options);
storeDiscoveryManagerRequestMap(clientRequestId, transactionId, listener, storeDiscoveryManagerRequestMap(clientRequestId, transactionId, listener,
clientInfo, info.getNetwork()); clientInfo, info.getNetwork());
clientInfo.onServiceInfoCallbackRegistered(transactionId);
clientInfo.log("Register a ServiceInfoListener " + transactionId clientInfo.log("Register a ServiceInfoListener " + transactionId
+ " for service type:" + resolveServiceType); + " for service type:" + resolveServiceType);
break; break;
@@ -1140,7 +1141,7 @@ public class NsdService extends INsdManager.Stub {
if (request instanceof DiscoveryManagerRequest) { if (request instanceof DiscoveryManagerRequest) {
stopDiscoveryManagerRequest( stopDiscoveryManagerRequest(
request, clientRequestId, transactionId, clientInfo); request, clientRequestId, transactionId, clientInfo);
clientInfo.onServiceInfoCallbackUnregistered(clientRequestId); clientInfo.onServiceInfoCallbackUnregistered(clientRequestId, request);
clientInfo.log("Unregister the ServiceInfoListener " + transactionId); clientInfo.log("Unregister the ServiceInfoListener " + transactionId);
} else { } else {
loge("Unregister failed with non-DiscoveryManagerRequest."); loge("Unregister failed with non-DiscoveryManagerRequest.");
@@ -1478,11 +1479,17 @@ public class NsdService extends INsdManager.Stub {
final List<InetAddress> addresses = getInetAddresses(serviceInfo); final List<InetAddress> addresses = getInetAddresses(serviceInfo);
info.setHostAddresses(addresses); info.setHostAddresses(addresses);
clientInfo.onServiceUpdated(clientRequestId, info); clientInfo.onServiceUpdated(clientRequestId, info, request);
// Set the ServiceFromCache flag only if the service is actually being
// retrieved from the cache. This flag should not be overridden by later
// service updates, which may not be cached.
if (event.mIsServiceFromCache) {
request.setServiceFromCache(true);
}
break; break;
} }
case NsdManager.SERVICE_UPDATED_LOST: case NsdManager.SERVICE_UPDATED_LOST:
clientInfo.onServiceUpdatedLost(clientRequestId); clientInfo.onServiceUpdatedLost(clientRequestId, request);
break; break;
default: default:
return false; return false;
@@ -2396,6 +2403,12 @@ public class NsdService extends INsdManager.Stub {
} else if (listener instanceof ResolutionListener) { } else if (listener instanceof ResolutionListener) {
mMetrics.reportServiceResolutionStop(transactionId, mMetrics.reportServiceResolutionStop(transactionId,
request.calculateRequestDurationMs(mClock.elapsedRealtime())); request.calculateRequestDurationMs(mClock.elapsedRealtime()));
} else if (listener instanceof ServiceInfoListener) {
mMetrics.reportServiceInfoCallbackUnregistered(transactionId,
request.calculateRequestDurationMs(mClock.elapsedRealtime()),
request.getFoundServiceCount(),
request.getLostServiceCount(),
request.isServiceFromCache());
} }
continue; continue;
} }
@@ -2622,6 +2635,7 @@ public class NsdService extends INsdManager.Stub {
} }
void onServiceInfoCallbackRegistrationFailed(int listenerKey, int error) { void onServiceInfoCallbackRegistrationFailed(int listenerKey, int error) {
mMetrics.reportServiceInfoCallbackRegistrationFailed(NO_TRANSACTION);
try { try {
mCb.onServiceInfoCallbackRegistrationFailed(listenerKey, error); mCb.onServiceInfoCallbackRegistrationFailed(listenerKey, error);
} catch (RemoteException e) { } catch (RemoteException e) {
@@ -2629,7 +2643,12 @@ public class NsdService extends INsdManager.Stub {
} }
} }
void onServiceUpdated(int listenerKey, NsdServiceInfo info) { void onServiceInfoCallbackRegistered(int transactionId) {
mMetrics.reportServiceInfoCallbackRegistered(transactionId);
}
void onServiceUpdated(int listenerKey, NsdServiceInfo info, ClientRequest request) {
request.onServiceFound(info.getServiceName());
try { try {
mCb.onServiceUpdated(listenerKey, info); mCb.onServiceUpdated(listenerKey, info);
} catch (RemoteException e) { } catch (RemoteException e) {
@@ -2637,7 +2656,8 @@ public class NsdService extends INsdManager.Stub {
} }
} }
void onServiceUpdatedLost(int listenerKey) { void onServiceUpdatedLost(int listenerKey, ClientRequest request) {
request.onServiceLost();
try { try {
mCb.onServiceUpdatedLost(listenerKey); mCb.onServiceUpdatedLost(listenerKey);
} catch (RemoteException e) { } catch (RemoteException e) {
@@ -2645,7 +2665,13 @@ public class NsdService extends INsdManager.Stub {
} }
} }
void onServiceInfoCallbackUnregistered(int listenerKey) { void onServiceInfoCallbackUnregistered(int listenerKey, ClientRequest request) {
mMetrics.reportServiceInfoCallbackUnregistered(
request.mTransactionId,
request.calculateRequestDurationMs(mClock.elapsedRealtime()),
request.getFoundServiceCount(),
request.getLostServiceCount(),
request.isServiceFromCache());
try { try {
mCb.onServiceInfoCallbackUnregistered(listenerKey); mCb.onServiceInfoCallbackUnregistered(listenerKey);
} catch (RemoteException e) { } catch (RemoteException e) {

View File

@@ -221,4 +221,67 @@ class NetworkNsdReportedMetricsTest {
assertEquals(durationMs, it.eventDurationMillisec) assertEquals(durationMs, it.eventDurationMillisec)
} }
} }
@Test
fun testReportServiceInfoCallbackRegistered() {
val clientId = 99
val transactionId = 100
val metrics = NetworkNsdReportedMetrics(false /* isLegacy */, clientId, deps)
metrics.reportServiceInfoCallbackRegistered(transactionId)
val eventCaptor = ArgumentCaptor.forClass(NetworkNsdReported::class.java)
verify(deps).statsWrite(eventCaptor.capture())
eventCaptor.value.let {
assertFalse(it.isLegacy)
assertEquals(clientId, it.clientId)
assertEquals(transactionId, it.transactionId)
assertEquals(NsdEventType.NET_SERVICE_INFO_CALLBACK, it.type)
assertEquals(MdnsQueryResult.MQR_SERVICE_INFO_CALLBACK_REGISTERED, it.queryResult)
}
}
@Test
fun testReportServiceInfoCallbackRegistrationFailed() {
val clientId = 99
val transactionId = 100
val metrics = NetworkNsdReportedMetrics(true /* isLegacy */, clientId, deps)
metrics.reportServiceInfoCallbackRegistrationFailed(transactionId)
val eventCaptor = ArgumentCaptor.forClass(NetworkNsdReported::class.java)
verify(deps).statsWrite(eventCaptor.capture())
eventCaptor.value.let {
assertTrue(it.isLegacy)
assertEquals(clientId, it.clientId)
assertEquals(transactionId, it.transactionId)
assertEquals(NsdEventType.NET_SERVICE_INFO_CALLBACK, it.type)
assertEquals(
MdnsQueryResult.MQR_SERVICE_INFO_CALLBACK_REGISTRATION_FAILED, it.queryResult)
}
}
@Test
fun testReportServiceInfoCallbackUnregistered() {
val clientId = 99
val transactionId = 100
val durationMs = 10L
val updateCallbackCount = 100
val lostCallbackCount = 10
val metrics = NetworkNsdReportedMetrics(false /* isLegacy */, clientId, deps)
metrics.reportServiceInfoCallbackUnregistered(transactionId, durationMs,
updateCallbackCount, lostCallbackCount, false /* isServiceFromCache */)
val eventCaptor = ArgumentCaptor.forClass(NetworkNsdReported::class.java)
verify(deps).statsWrite(eventCaptor.capture())
eventCaptor.value.let {
assertFalse(it.isLegacy)
assertEquals(clientId, it.clientId)
assertEquals(transactionId, it.transactionId)
assertEquals(NsdEventType.NET_SERVICE_INFO_CALLBACK, it.type)
assertEquals(MdnsQueryResult.MQR_SERVICE_INFO_CALLBACK_UNREGISTERED, it.queryResult)
assertEquals(durationMs, it.eventDurationMillisec)
assertEquals(updateCallbackCount, it.foundCallbackCount)
assertEquals(lostCallbackCount, it.lostCallbackCount)
assertFalse(it.isKnownService)
}
}
} }

View File

@@ -822,13 +822,17 @@ public class NsdServiceTest {
client.registerServiceInfoCallback(request, Runnable::run, serviceInfoCallback); client.registerServiceInfoCallback(request, Runnable::run, serviceInfoCallback);
waitForIdle(); waitForIdle();
// Verify the registration callback start. // Verify the registration callback start.
final ArgumentCaptor<MdnsServiceBrowserListener> listenerCaptor = final ArgumentCaptor<MdnsListener> listenerCaptor =
ArgumentCaptor.forClass(MdnsServiceBrowserListener.class); ArgumentCaptor.forClass(MdnsListener.class);
verify(mSocketProvider).startMonitoringSockets(); verify(mSocketProvider).startMonitoringSockets();
verify(mDiscoveryManager).registerListener(eq(serviceTypeWithLocalDomain), verify(mDiscoveryManager).registerListener(eq(serviceTypeWithLocalDomain),
listenerCaptor.capture(), argThat(options -> network.equals(options.getNetwork()))); listenerCaptor.capture(), argThat(options -> network.equals(options.getNetwork())));
final MdnsServiceBrowserListener listener = listenerCaptor.getValue(); final MdnsListener listener = listenerCaptor.getValue();
final int servInfoId = listener.mTransactionId;
// Verify the service info callback registered.
verify(mMetrics).reportServiceInfoCallbackRegistered(servInfoId);
final MdnsServiceInfo mdnsServiceInfo = new MdnsServiceInfo( final MdnsServiceInfo mdnsServiceInfo = new MdnsServiceInfo(
SERVICE_NAME, SERVICE_NAME,
serviceTypeWithLocalDomain.split("\\."), serviceTypeWithLocalDomain.split("\\."),
@@ -842,8 +846,11 @@ public class NsdServiceTest {
1234, 1234,
network); network);
// Callbacks for query sent.
listener.onDiscoveryQuerySent(Collections.emptyList(), 1 /* transactionId */);
// Verify onServiceFound callback // Verify onServiceFound callback
listener.onServiceFound(mdnsServiceInfo, false /* isServiceFromCache */); listener.onServiceFound(mdnsServiceInfo, true /* isServiceFromCache */);
final ArgumentCaptor<NsdServiceInfo> updateInfoCaptor = final ArgumentCaptor<NsdServiceInfo> updateInfoCaptor =
ArgumentCaptor.forClass(NsdServiceInfo.class); ArgumentCaptor.forClass(NsdServiceInfo.class);
verify(serviceInfoCallback, timeout(TIMEOUT_MS).times(1)) verify(serviceInfoCallback, timeout(TIMEOUT_MS).times(1))
@@ -878,10 +885,18 @@ public class NsdServiceTest {
List.of(parseNumericAddress(v4Address), parseNumericAddress(v6Address)), List.of(parseNumericAddress(v4Address), parseNumericAddress(v6Address)),
PORT, IFACE_IDX_ANY, new Network(999)); PORT, IFACE_IDX_ANY, new Network(999));
// Service lost then recovered.
listener.onServiceRemoved(updatedServiceInfo);
listener.onServiceFound(updatedServiceInfo, false /* isServiceFromCache */);
// Verify service callback unregistration. // Verify service callback unregistration.
doReturn(TEST_TIME_MS + 10L).when(mClock).elapsedRealtime();
client.unregisterServiceInfoCallback(serviceInfoCallback); client.unregisterServiceInfoCallback(serviceInfoCallback);
waitForIdle(); waitForIdle();
verify(serviceInfoCallback, timeout(TIMEOUT_MS)).onServiceInfoCallbackUnregistered(); verify(serviceInfoCallback, timeout(TIMEOUT_MS)).onServiceInfoCallbackUnregistered();
verify(mMetrics).reportServiceInfoCallbackUnregistered(servInfoId, 10L /* durationMs */,
3 /* updateCallbackCount */, 1 /* lostCallbackCount */,
true /* isServiceFromCache */);
} }
@Test @Test
@@ -897,6 +912,7 @@ public class NsdServiceTest {
// Fail to register service callback. // Fail to register service callback.
verify(serviceInfoCallback, timeout(TIMEOUT_MS)) verify(serviceInfoCallback, timeout(TIMEOUT_MS))
.onServiceInfoCallbackRegistrationFailed(eq(FAILURE_BAD_PARAMETERS)); .onServiceInfoCallbackRegistrationFailed(eq(FAILURE_BAD_PARAMETERS));
verify(mMetrics).reportServiceInfoCallbackRegistrationFailed(NO_TRANSACTION);
} }
@Test @Test