use of com.aws.greengrass.mqttclient.PublishRequest in project aws-greengrass-nucleus by aws-greengrass.
the class PeriodicFleetStatusServiceTest method setupKernel.
@BeforeEach
void setupKernel(ExtensionContext context) throws Exception {
ignoreExceptionOfType(context, TLSAuthException.class);
CountDownLatch fssRunning = new CountDownLatch(1);
CountDownLatch deploymentServiceRunning = new CountDownLatch(1);
AtomicBoolean mainServiceFinished = new AtomicBoolean();
allComponentsInFssUpdate = new CountDownLatch(1);
fleetStatusDetails = new AtomicReference<>();
CompletableFuture cf = new CompletableFuture();
cf.complete(null);
kernel = new Kernel();
when(DEFAULT_HANDLER.retrieveWithDefault(any(), eq(TELEMETRY_TEST_PERIODIC_AGGREGATE_INTERVAL_SEC), any())).thenReturn(DEFAULT_PERIODIC_AGGREGATE_INTERVAL_SEC);
when(DEFAULT_HANDLER.retrieveWithDefault(any(), eq(TELEMETRY_TEST_PERIODIC_PUBLISH_INTERVAL_SEC), any())).thenReturn(DEFAULT_PERIODIC_PUBLISH_INTERVAL_SEC);
when(DEFAULT_HANDLER.retrieveWithDefault(any(), eq(FLEET_STATUS_TEST_PERIODIC_UPDATE_INTERVAL_SEC), any())).thenReturn(FSS_UPDATE_INTERVAL);
TestFeatureParameters.internalEnableTestingFeatureParameters(DEFAULT_HANDLER);
ConfigPlatformResolver.initKernelWithMultiPlatformConfig(kernel, IotJobsFleetStatusServiceTest.class.getResource("onlyMain.yaml"));
kernel.getContext().put(MqttClient.class, mqttClient);
when(mqttClient.publish(any(PublishRequest.class))).thenAnswer(i -> {
Object argument = i.getArgument(0);
PublishRequest publishRequest = (PublishRequest) argument;
try {
fleetStatusDetails.set(OBJECT_MAPPER.readValue(publishRequest.getPayload(), FleetStatusDetails.class));
if (mainServiceFinished.get() && kernel.orderedDependencies().size() == fleetStatusDetails.get().getComponentStatusDetails().size()) {
allComponentsInFssUpdate.countDown();
}
} catch (JsonMappingException ignored) {
}
return CompletableFuture.completedFuture(0);
});
kernel.getContext().addGlobalStateChangeListener((service, oldState, newState) -> {
if (service.getName().equals(FleetStatusService.FLEET_STATUS_SERVICE_TOPICS)) {
if (newState.equals(State.RUNNING)) {
fssRunning.countDown();
}
FleetStatusService fleetStatusService = (FleetStatusService) service;
fleetStatusService.setPeriodicPublishIntervalSec(FSS_UPDATE_INTERVAL);
fleetStatusService.schedulePeriodicFleetStatusDataUpdate(false);
}
if (service.getName().equals(DeploymentService.DEPLOYMENT_SERVICE_TOPICS) && newState.equals(State.RUNNING)) {
deploymentServiceRunning.countDown();
}
if (service.getName().equals(KernelCommandLine.MAIN_SERVICE_NAME) && newState.equals(State.FINISHED)) {
mainServiceFinished.set(true);
}
});
// set required instances from context
deviceConfiguration = new DeviceConfiguration(kernel, "ThingName", "xxxxxx-ats.iot.us-east-1.amazonaws.com", "xxxxxx.credentials.iot.us-east-1.amazonaws.com", "privKeyFilePath", "certFilePath", "caFilePath", "us-east-1", "roleAliasName");
kernel.getContext().put(DeviceConfiguration.class, deviceConfiguration);
kernel.launch();
assertTrue(deploymentServiceRunning.await(10, TimeUnit.SECONDS));
assertTrue(fssRunning.await(10, TimeUnit.SECONDS));
}
use of com.aws.greengrass.mqttclient.PublishRequest in project aws-greengrass-nucleus by aws-greengrass.
the class TelemetryAgentTest method GIVEN_kernel_running_with_telemetry_config_WHEN_launch_THEN_metrics_are_published.
@Test
void GIVEN_kernel_running_with_telemetry_config_WHEN_launch_THEN_metrics_are_published(ExtensionContext context) throws InterruptedException, IOException, DeviceConfigurationException {
// Ignore exceptions caused by mock device configs
ignoreExceptionOfType(context, SdkClientException.class);
ignoreExceptionOfType(context, TLSAuthException.class);
// GIVEN
ConfigPlatformResolver.initKernelWithMultiPlatformConfig(kernel, this.getClass().getResource("config.yaml"));
kernel.getContext().put(MqttClient.class, mqttClient);
kernel.getContext().put(DeviceConfiguration.class, new DeviceConfiguration(kernel, MOCK_THING_NAME, "us-east-1", "us-east-1", "mock", "mock", "mock", "us-east-1", "mock"));
// WHEN
CountDownLatch telemetryRunning = new CountDownLatch(1);
kernel.getContext().addGlobalStateChangeListener((service, oldState, newState) -> {
if (service.getName().equals(TELEMETRY_AGENT_SERVICE_TOPICS)) {
if (service.getState().equals(State.RUNNING)) {
ta = (TelemetryAgent) service;
telemetryRunning.countDown();
}
}
});
kernel.launch();
assertTrue(telemetryRunning.await(10, TimeUnit.SECONDS), "TelemetryAgent is not in RUNNING state.");
Topics telTopics = kernel.findServiceTopic(TELEMETRY_AGENT_SERVICE_TOPICS);
assertNotNull(telTopics);
long lastAgg = Coerce.toLong(telTopics.find(RUNTIME_STORE_NAMESPACE_TOPIC, TELEMETRY_LAST_PERIODIC_AGGREGATION_TIME_TOPIC));
// wait till the first publish
TimeUnit.SECONDS.sleep(publishInterval + 1);
assertTrue(Coerce.toLong(telTopics.find(RUNTIME_STORE_NAMESPACE_TOPIC, TELEMETRY_LAST_PERIODIC_AGGREGATION_TIME_TOPIC)) > lastAgg);
assertNotNull(ta.getPeriodicPublishMetricsFuture(), "periodic publish future is not scheduled.");
long delay = ta.getPeriodicPublishMetricsFuture().getDelay(TimeUnit.SECONDS);
assertTrue(delay <= publishInterval);
// telemetry logs are always written to ~root/telemetry
assertEquals(kernel.getNucleusPaths().rootPath().resolve("telemetry"), TelemetryConfig.getTelemetryDirectory());
// THEN
boolean telemetryMessageVerified = false;
if (delay < aggregateInterval) {
verify(mqttClient, atLeast(0)).publish(captor.capture());
} else {
verify(mqttClient, atLeastOnce()).publish(captor.capture());
List<PublishRequest> prs = captor.getAllValues();
String telemetryPublishTopic = DEFAULT_TELEMETRY_METRICS_PUBLISH_TOPIC.replace("{thingName}", MOCK_THING_NAME);
for (PublishRequest pr : prs) {
// filter for telemetry topic because messages published to irrelevant topics can be captured here
if (!telemetryPublishTopic.equals(pr.getTopic())) {
continue;
}
try {
MetricsPayload mp = new ObjectMapper().readValue(pr.getPayload(), MetricsPayload.class);
assertEquals(QualityOfService.AT_LEAST_ONCE, pr.getQos());
assertEquals("2020-07-30", mp.getSchema());
// enough to verify the first message of type MetricsPayload
telemetryMessageVerified = true;
break;
} catch (IOException e) {
fail("The message received at this topic is not of MetricsPayload type.", e);
}
}
assertTrue(telemetryMessageVerified, "Did not see message published to telemetry metrics topic");
}
}
use of com.aws.greengrass.mqttclient.PublishRequest in project aws-greengrass-nucleus by aws-greengrass.
the class MqttClientPublishTest method GIVEN_MqttProxyEventStreamClient_WHEN_publish_THEN_message_published.
@Test
void GIVEN_MqttProxyEventStreamClient_WHEN_publish_THEN_message_published() throws Exception {
PublishToIoTCoreRequest publishToIoTCoreRequest = new PublishToIoTCoreRequest();
publishToIoTCoreRequest.setPayload(TEST_GOOD_PAYLOAD);
publishToIoTCoreRequest.setQos(QOS.AT_LEAST_ONCE);
publishToIoTCoreRequest.setTopicName(TEST_GOOD_PUBLISH_TOPIC);
greengrassCoreIPCClient.publishToIoTCore(publishToIoTCoreRequest, Optional.empty()).getResponse().get(TIMEOUT_FOR_MQTTPROXY_SECONDS, TimeUnit.SECONDS);
ArgumentCaptor<PublishRequest> publishRequestArgumentCaptor = ArgumentCaptor.forClass(PublishRequest.class);
verify(mqttClient).publish(publishRequestArgumentCaptor.capture());
PublishRequest capturedPublishRequest = publishRequestArgumentCaptor.getValue();
assertThat(capturedPublishRequest.getPayload(), is(TEST_GOOD_PAYLOAD));
assertThat(capturedPublishRequest.getTopic(), is(TEST_GOOD_PUBLISH_TOPIC));
assertThat(capturedPublishRequest.getQos(), is(QualityOfService.AT_LEAST_ONCE));
}
use of com.aws.greengrass.mqttclient.PublishRequest in project aws-greengrass-nucleus by aws-greengrass.
the class TelemetryAgentTest method GIVEN_Telemetry_Agent_WHEN_mqtt_is_interrupted_THEN_aggregation_continues_but_publishing_stops.
@Test
void GIVEN_Telemetry_Agent_WHEN_mqtt_is_interrupted_THEN_aggregation_continues_but_publishing_stops() {
doReturn(1).when(DEFAULT_HANDLER).retrieveWithDefault(any(), eq(TELEMETRY_TEST_PERIODIC_AGGREGATE_INTERVAL_SEC), any());
doReturn(2).when(DEFAULT_HANDLER).retrieveWithDefault(any(), eq(TELEMETRY_TEST_PERIODIC_PUBLISH_INTERVAL_SEC), any());
TestFeatureParameters.internalEnableTestingFeatureParameters(DEFAULT_HANDLER);
Map<Long, List<AggregatedNamespaceData>> metricsToPublishMap = new HashMap<>();
List<AggregatedNamespaceData> data = new ArrayList<>();
data.add(AggregatedNamespaceData.builder().namespace("SomeNameSpace").build());
when(ma.getMetricsToPublish(anyLong(), publishTimeArgumentCaptor.capture())).thenAnswer(invocation -> {
metricsToPublishMap.put(publishTimeArgumentCaptor.getValue(), data);
return metricsToPublishMap;
});
telemetryAgent.postInject();
long timeoutMs = 10000;
verify(mockMqttClient, timeout(timeoutMs).atLeastOnce()).publish(publishRequestArgumentCaptor.capture());
PublishRequest request = publishRequestArgumentCaptor.getValue();
assertEquals(QualityOfService.AT_LEAST_ONCE, request.getQos());
assertEquals("$aws/things/testThing/greengrass/health/json", request.getTopic());
reset(mockMqttClient);
mqttClientConnectionEventsArgumentCaptor.getValue().onConnectionInterrupted(500);
// verify that nothing is published when mqtt is interrupted
verify(mockMqttClient, times(0)).publish(publishRequestArgumentCaptor.capture());
// aggregation is continued irrespective of the mqtt connection
verify(ma, timeout(timeoutMs).atLeastOnce()).aggregateMetrics(anyLong(), anyLong());
}
use of com.aws.greengrass.mqttclient.PublishRequest in project aws-greengrass-nucleus by aws-greengrass.
the class FleetStatusServiceTest method GIVEN_large_num_component_status_change_WHEN_deployment_finishes_THEN_MQTT_Sent_with_fss_data_with_overall_healthy_state.
@Test
void GIVEN_large_num_component_status_change_WHEN_deployment_finishes_THEN_MQTT_Sent_with_fss_data_with_overall_healthy_state() throws ServiceLoadException, IOException, InterruptedException {
// Set up all the topics
int numServices = 1500;
Topics statusConfigTopics = Topics.of(context, FLEET_STATUS_CONFIG_TOPICS, null);
statusConfigTopics.createLeafChild(FLEET_STATUS_PERIODIC_PUBLISH_INTERVAL_SEC).withValue("10000");
Topics allComponentToGroupsTopics = Topics.of(context, GROUP_TO_ROOT_COMPONENTS_TOPICS, null);
Topic groupTopic1 = Topic.of(context, "arn:aws:greengrass:testRegion:12345:configuration:testGroup:12", true);
List<GreengrassService> greengrassServices = new ArrayList<>();
Set<String> serviceNamesToCheck = new HashSet<>();
for (int i = 0; i < numServices; i++) {
String serviceName = String.format("MockService-%s", i);
Topics groupsTopics = Topics.of(context, serviceName, allComponentToGroupsTopics);
groupsTopics.children.put(new CaseInsensitiveString(serviceName), groupTopic1);
allComponentToGroupsTopics.children.put(new CaseInsensitiveString(serviceName), groupsTopics);
GreengrassService greengrassService = mock(GreengrassService.class);
when(greengrassService.getName()).thenReturn(serviceName);
when(greengrassService.getState()).thenReturn(State.RUNNING);
when(greengrassService.getServiceConfig()).thenReturn(config);
greengrassServices.add(greengrassService);
serviceNamesToCheck.add(serviceName);
when(mockKernel.locate(serviceName)).thenReturn(greengrassService);
}
lenient().when(config.lookupTopics(COMPONENTS_TO_GROUPS_TOPICS)).thenReturn(allComponentToGroupsTopics);
// Set up all the mocks
when(mockDeploymentStatusKeeper.registerDeploymentStatusConsumer(any(), consumerArgumentCaptor.capture(), anyString())).thenReturn(true);
when(mockKernel.locate(DeploymentService.DEPLOYMENT_SERVICE_TOPICS)).thenReturn(mockDeploymentService);
when(mockKernel.orderedDependencies()).thenReturn(greengrassServices);
when(mockDeploymentService.getConfig()).thenReturn(config);
doNothing().when(context).addGlobalStateChangeListener(addGlobalStateChangeListenerArgumentCaptor.capture());
when(mockDeviceConfiguration.getStatusConfigurationTopics()).thenReturn(statusConfigTopics);
when(context.get(ScheduledExecutorService.class)).thenReturn(ses);
// Create the fleet status service instance
fleetStatusService = createFSS();
fleetStatusService.startup();
// Update the job status for an ongoing deployment to SUCCEEDED.
Map<String, Object> map = new HashMap<>();
map.put(DEPLOYMENT_STATUS_KEY_NAME, JobStatus.IN_PROGRESS.toString());
map.put(DEPLOYMENT_ID_KEY_NAME, "testJob");
map.put(DEPLOYMENT_TYPE_KEY_NAME, IOT_JOBS);
consumerArgumentCaptor.getValue().apply(map);
// Update the state of an EG service.
for (int i = 0; i < numServices; i++) {
addGlobalStateChangeListenerArgumentCaptor.getValue().globalServiceStateChanged(greengrassServices.get(i), State.INSTALLED, State.RUNNING);
}
// Update the job status for an ongoing deployment to SUCCEEDED.
map.put(DEPLOYMENT_STATUS_KEY_NAME, JobStatus.SUCCEEDED.toString());
consumerArgumentCaptor.getValue().apply(map);
// Verify that an MQTT message with the components' status is uploaded.
verify(mockMqttClient, times(3)).publish(publishRequestArgumentCaptor.capture());
List<PublishRequest> publishRequests = publishRequestArgumentCaptor.getAllValues();
ObjectMapper mapper = new ObjectMapper();
for (PublishRequest publishRequest : publishRequests) {
assertEquals(QualityOfService.AT_LEAST_ONCE, publishRequest.getQos());
assertEquals("$aws/things/testThing/greengrassv2/health/json", publishRequest.getTopic());
FleetStatusDetails fleetStatusDetails = mapper.readValue(publishRequest.getPayload(), FleetStatusDetails.class);
assertEquals(VERSION, fleetStatusDetails.getGgcVersion());
assertEquals("testThing", fleetStatusDetails.getThing());
assertEquals(OverallStatus.HEALTHY, fleetStatusDetails.getOverallStatus());
assertEquals(500, fleetStatusDetails.getComponentStatusDetails().size());
for (ComponentStatusDetails componentStatusDetails : fleetStatusDetails.getComponentStatusDetails()) {
serviceNamesToCheck.remove(componentStatusDetails.getComponentName());
assertNull(componentStatusDetails.getStatusDetails());
assertEquals(State.RUNNING, componentStatusDetails.getState());
assertEquals(Collections.singletonList("arn:aws:greengrass:testRegion:12345:configuration:testGroup:12"), componentStatusDetails.getFleetConfigArns());
}
}
assertThat(serviceNamesToCheck, is(IsEmptyCollection.empty()));
}
Aggregations