def Run(self, arg): """Returns the client stats.""" if arg is None: arg = rdfvalue.GetClientStatsRequest() proc = psutil.Process(os.getpid()) meminfo = proc.memory_info() response = rdfvalue.ClientStats( RSS_size=meminfo[0], VMS_size=meminfo[1], memory_percent=proc.memory_percent(), bytes_received=stats.STATS.GetMetricValue( "grr_client_received_bytes"), bytes_sent=stats.STATS.GetMetricValue("grr_client_sent_bytes"), create_time=long(proc.create_time() * 1e6), boot_time=long(psutil.boot_time() * 1e6)) samples = self.grr_worker.stats_collector.cpu_samples for (timestamp, user, system, percent) in samples: if arg.start_time < timestamp < arg.end_time: sample = rdfvalue.CpuSample(timestamp=timestamp, user_cpu_time=user, system_cpu_time=system, cpu_percent=percent) response.cpu_samples.Append(sample) samples = self.grr_worker.stats_collector.io_samples for (timestamp, read_bytes, write_bytes) in samples: if arg.start_time < timestamp < arg.end_time: sample = rdfvalue.IOSample(timestamp=timestamp, read_bytes=read_bytes, write_bytes=write_bytes) response.io_samples.Append(sample) self.Send(response)
def CheckStats(self): """Checks if the last transmission of client stats is too long ago.""" if self.last_stats_sent_time is None: self.last_stats_sent_time = rdfvalue.RDFDatetime().Now() stats.STATS.SetGaugeValue( "grr_client_last_stats_sent_time", self.last_stats_sent_time.AsSecondsFromEpoch()) time_since_last_check = (rdfvalue.RDFDatetime().Now() - self.last_stats_sent_time) # No matter what, we don't want to send stats more often than # once per STATS_MIN_SEND_INTERVAL. if time_since_last_check < self.STATS_MIN_SEND_INTERVAL: return if (time_since_last_check > self.STATS_MAX_SEND_INTERVAL or self._is_active or self._send_stats_on_check): self._send_stats_on_check = False logging.info("Sending back client statistics to the server.") action_cls = actions.ActionPlugin.classes.get( "GetClientStatsAuto", actions.ActionPlugin) action = action_cls(grr_worker=self) action.Run( rdfvalue.GetClientStatsRequest( start_time=self.last_stats_sent_time)) self.last_stats_sent_time = rdfvalue.RDFDatetime().Now() stats.STATS.SetGaugeValue( "grr_client_last_stats_sent_time", self.last_stats_sent_time.AsSecondsFromEpoch())
def testReturnsAllDataByDefault(self): """Checks that stats collection works.""" stats.STATS.RegisterCounterMetric("grr_client_received_bytes") stats.STATS.IncrementCounter("grr_client_received_bytes", 1566) stats.STATS.RegisterCounterMetric("grr_client_sent_bytes") stats.STATS.IncrementCounter("grr_client_sent_bytes", 2000) results = self.RunAction("GetClientStats", grr_worker=MockClientWorker(), arg=rdfvalue.GetClientStatsRequest()) response = results[0] self.assertEqual(response.bytes_received, 1566) self.assertEqual(response.bytes_sent, 2000) self.assertEqual(len(response.cpu_samples), 3) for i in range(3): self.assertEqual(response.cpu_samples[i].timestamp, rdfvalue.RDFDatetime().FromSecondsFromEpoch( 100 + i * 10)) self.assertAlmostEqual(response.cpu_samples[i].user_cpu_time, 0.1) self.assertAlmostEqual(response.cpu_samples[i].system_cpu_time, 0.1 * (i + 1)) self.assertAlmostEqual(response.cpu_samples[i].cpu_percent, 10.0 + 5 * i) self.assertEqual(len(response.io_samples), 3) for i in range(3): self.assertEqual(response.io_samples[i].timestamp, rdfvalue.RDFDatetime().FromSecondsFromEpoch( 100 + i * 10)) self.assertEqual(response.io_samples[i].read_bytes, 100 * (i + 1)) self.assertEqual(response.io_samples[i].write_bytes, 100 * (i + 1)) self.assertEqual(response.boot_time, long(100 * 1e6))
def testFiltersDataPointsByEndTime(self): end_time = rdfvalue.RDFDatetime().FromSecondsFromEpoch(102) results = self.RunAction( "GetClientStats", grr_worker=MockClientWorker(), arg=rdfvalue.GetClientStatsRequest(end_time=end_time)) response = results[0] self.assertEqual(len(response.cpu_samples), 1) self.assertEqual(response.cpu_samples[0].timestamp, rdfvalue.RDFDatetime().FromSecondsFromEpoch(100)) self.assertEqual(len(response.io_samples), 1) self.assertEqual(response.io_samples[0].timestamp, rdfvalue.RDFDatetime().FromSecondsFromEpoch(100))