blob: 053025838ac7d57501e4739dd4bd0ac86087a8c4 [file] [log] [blame]
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<!-- NewPage -->
<html lang="en">
<head>
<!-- Generated by javadoc (1.8.0_112) on Sun Feb 26 17:08:12 EST 2017 -->
<title>org.apache.edgent.samples.apps.sensorAnalytics (Edgent v1.1.0)</title>
<meta name="date" content="2017-02-26">
<link rel="stylesheet" type="text/css" href="../../../../../../stylesheet.css" title="Style">
<script type="text/javascript" src="../../../../../../script.js"></script>
</head>
<body>
<script type="text/javascript"><!--
try {
if (location.href.indexOf('is-external=true') == -1) {
parent.document.title="org.apache.edgent.samples.apps.sensorAnalytics (Edgent v1.1.0)";
}
}
catch(err) {
}
//-->
</script>
<noscript>
<div>JavaScript is disabled on your browser.</div>
</noscript>
<!-- ========= START OF TOP NAVBAR ======= -->
<div class="topNav"><a name="navbar.top">
<!-- -->
</a>
<div class="skipNav"><a href="#skip.navbar.top" title="Skip navigation links">Skip navigation links</a></div>
<a name="navbar.top.firstrow">
<!-- -->
</a>
<ul class="navList" title="Navigation">
<li><a href="../../../../../../overview-summary.html">Overview</a></li>
<li class="navBarCell1Rev">Package</li>
<li>Class</li>
<li><a href="package-use.html">Use</a></li>
<li><a href="package-tree.html">Tree</a></li>
<li><a href="../../../../../../deprecated-list.html">Deprecated</a></li>
<li><a href="../../../../../../index-all.html">Index</a></li>
<li><a href="../../../../../../help-doc.html">Help</a></li>
</ul>
</div>
<div class="subNav">
<ul class="navList">
<li><a href="../../../../../../org/apache/edgent/samples/apps/mqtt/package-summary.html">Prev&nbsp;Package</a></li>
<li><a href="../../../../../../org/apache/edgent/samples/connectors/package-summary.html">Next&nbsp;Package</a></li>
</ul>
<ul class="navList">
<li><a href="../../../../../../index.html?org/apache/edgent/samples/apps/sensorAnalytics/package-summary.html" target="_top">Frames</a></li>
<li><a href="package-summary.html" target="_top">No&nbsp;Frames</a></li>
</ul>
<ul class="navList" id="allclasses_navbar_top">
<li><a href="../../../../../../allclasses-noframe.html">All&nbsp;Classes</a></li>
</ul>
<div>
<script type="text/javascript"><!--
allClassesLink = document.getElementById("allclasses_navbar_top");
if(window==top) {
allClassesLink.style.display = "block";
}
else {
allClassesLink.style.display = "none";
}
//-->
</script>
</div>
<a name="skip.navbar.top">
<!-- -->
</a></div>
<!-- ========= END OF TOP NAVBAR ========= -->
<div class="header">
<h1 title="Package" class="title">Package&nbsp;org.apache.edgent.samples.apps.sensorAnalytics</h1>
<div class="docSummary">
<div class="block">The Sensor Analytics sample application demonstrates some common
continuous sensor analytic application themes.</div>
</div>
<p>See:&nbsp;<a href="#package.description">Description</a></p>
</div>
<div class="contentContainer">
<ul class="blockList">
<li class="blockList">
<table class="typeSummary" border="0" cellpadding="3" cellspacing="0" summary="Class Summary table, listing classes, and an explanation">
<caption><span>Class Summary</span><span class="tabEnd">&nbsp;</span></caption>
<tr>
<th class="colFirst" scope="col">Class</th>
<th class="colLast" scope="col">Description</th>
</tr>
<tbody>
<tr class="altColor">
<td class="colFirst"><a href="../../../../../../org/apache/edgent/samples/apps/sensorAnalytics/Sensor1.html" title="class in org.apache.edgent.samples.apps.sensorAnalytics">Sensor1</a></td>
<td class="colLast">
<div class="block">Analytics for "Sensor1".</div>
</td>
</tr>
<tr class="rowColor">
<td class="colFirst"><a href="../../../../../../org/apache/edgent/samples/apps/sensorAnalytics/SensorAnalyticsApplication.html" title="class in org.apache.edgent.samples.apps.sensorAnalytics">SensorAnalyticsApplication</a></td>
<td class="colLast">
<div class="block">A sample application demonstrating some common sensor analytic processing
themes.</div>
</td>
</tr>
</tbody>
</table>
</li>
</ul>
<a name="package.description">
<!-- -->
</a>
<h2 title="Package org.apache.edgent.samples.apps.sensorAnalytics Description">Package org.apache.edgent.samples.apps.sensorAnalytics Description</h2>
<div class="block">The Sensor Analytics sample application demonstrates some common
continuous sensor analytic application themes.
See <a href="../../../../../../org/apache/edgent/samples/apps/sensorAnalytics/Sensor1.html" title="class in org.apache.edgent.samples.apps.sensorAnalytics"><code>Sensor1</code></a> for the
core of the analytics processing and
<a href="../../../../../../org/apache/edgent/samples/apps/sensorAnalytics/SensorAnalyticsApplication.html" title="class in org.apache.edgent.samples.apps.sensorAnalytics"><code>SensorAnalyticsApplication</code></a>
for the main program.
<p>
The themes include:
<ul>
<li>Batched Data Reduction - reducing higher frequency sensor reading
samples down to a lower frequency using statistical aggregations
of the raw readings.
</li>
<li>Computing continuous historical statistics such as a
30 second trailing average of sensor readings.
</li>
<li>Outlier / threshold detection against a configurable range</li>
<li>Local logging of stream tuples</li>
<li>Publishing analytic results to an MQTT broker</li>
<li>Dynamic configuration control - subscribing to a MQTT broker
to receive commands to adjust the threshold detection range value.
</li>
<li>Generally, the configuration of the processing is driven via an
external configuration description.
</li>
<li>Conditional stream tracing - configuration controlled inclusion of tracing.
</li>
</ul>
<h2>Prerequisites:</h2>
<p>
The default configuration is for a local MQTT broker.
A good resource is <a href="http://mosquitto.org">mosquitto.org</a>
if you want to download and setup your own MQTT broker.
Or you can use some other broker available in your environment.
<p>
Alternatively, there are some public MQTT brokers available to experiment with.
Their availability status isn't guaranteed. If you're unable to connect
to the broker, it's likely that it isn't up or your firewalls don't
allow you to connect. DO NOT PUBLISH ANYTHING SENSITIVE - anyone
can be listing. A couple of public broker locations are noted
in the application's properties file.
<p>
The default <code>mqttDevice.topic.prefix</code> value, used by default in
generated MQTT topic values and MQTT clientId, contains the user's
local login id. The SensorAnalytics sample application does not have any
other sensitive information.
<p>
Edit <code>&lt;edgent-release&gt;/java8/scripts/apps/sensorAnalytics/sensoranalytics.properties</code>
to change the broker location or topic prefix.
<h2>Application output:</h2>
<p>
The application periodically (every 30sec), publishes a list of
the last 10 outliers to MQTT. When enabled, it also publishes
full details of individual outliers as they occur.
It also subscribes to MQTT topics for commands to dynamically change the
threshold range and whether to publish individual outliers.
<p>
All MQTT configuration information, including topic patterns,
are in the application.properties file.
<p>
The application logs outlier events in local files. The actual location
is specified in the application.properties file.
<p>
The application generates some output on stdout and stderr.
The information includes:
<ul>
<li>MQTT device info. Lines 1 through 5 in the sample console output below.</li>
<li>URL for the Edgent development console. Line 6.</li>
<li>Trace of the outlier event stream. Line 7.
The output is a label, which includes the active threshold range,
followed by the event's JSON.
These are the events that will also be logged and conditionally published
as well as included in the periodic lastN info published every 30sec.
</li>
<li>Announcement when a "change threshold" or "enable publish of 1khz outliers"
command is received and processed.
Line 8 and 9.
</li>
<li>At this time some INFO trace output from the MQTT connector</li>
<li>At this time some INFO trace output from the File connector</li>
</ul>
Sample console output:
<pre><code>
[1] MqttDevice serverURLs [tcp://localhost:1883]
[2] MqttDevice clientId id/012345
[3] MqttDevice deviceId 012345
[4] MqttDevice event topic pattern id/012345/evt/+/fmt/json
[5] MqttDevice command topic pattern id/012345/cmd/+/fmt/json
[6] Edgent Console URL for the job: http://localhost:57324/console
[7] sensor1.outside1hzMeanRange[124..129]: {"id":"sensor1","reading":{"N":1000,"MIN":0.0,"MAX":254.0,"MEAN":130.23200000000006,"STDDEV":75.5535473324351},"msec":1454623874408,"agg.begin.msec":1454623873410,"agg.count":1000,"AvgTrailingMean":128,"AvgTrailingMeanCnt":4}
...
[8] ===== Changing range to [125..127] ======
sensor1.outside1hzMeanRange[125..127]: {"id":"sensor1","reading":{"N":1000,"MIN":0.0,"MAX":254.0,"MEAN":129.00099999999978,"STDDEV":74.3076080870567},"msec":1454624142419,"agg.begin.msec":1454624141420,"agg.count":1000,"AvgTrailingMean":127,"AvgTrailingMeanCnt":30}
[9] ===== Changing isPublish1hzOutsideRange to true ======
...
</code></pre>
<h2>Running, observing and controlling the application:</h2>
<pre><code>
$ ./runSensorAnalytics.sh
</code></pre>
<p>
To observe the locally logged outlier events:
<pre><code>
$ tail -f /tmp/SensorAnalytics/logs/.outside1hzMeanRange
</code></pre>
<p>
To observe the events that are getting published to MQTT:
<pre><code>
$ ./runDeviceComms.sh watch
</code></pre>
<p>
To change the outlier threshold setting:
<br>The command value is the new range string: <code>[&lt;lowerBound&gt;..&lt;upperBound&gt;]</code>.
<pre><code>
$ ./runDeviceComms.sh send sensor1.set1hzMeanRangeThreshold "[125..127]"
</code></pre>
<p>
To change the "publish individual 1hz outliers" control:
<pre><code>
$ ./runDeviceComms.sh send sensor1.setPublish1hzOutsideRange true
</code></pre>
<h3>Alternative MQTT clients</h3>
You can use any MQTT client but you will have to specify the
MQTT server, the event topics to watch / subscribe to, and the command topics
and JSON for publish commands. The MqttDevice output above provides most
of the necessary information.
<p>
For example, the <code>mosquitto_pub</code> and
<code>mosquitto_sub</code> commands equivalent to the above runDeviceComms.sh
commands are:
<pre><code>
# Watch the device's event topics
$ /usr/local/bin/mosquitto_sub -t id/012345/evt/+/fmt/json
# change the outlier threshold setting
$ /usr/local/bin/mosquitto_pub -m '{"value":"[125..127]"}' -t id/012345/cmd/sensor1.set1hzMeanRangeThreshold/fmt/json
# change the "publish individual 1hz outliers" control
$ /usr/local/bin/mosquitto_pub -m '{"value":"true"}' -t id/012345/cmd/sensor1.setPublish1hzOutsideRange/fmt/json
</code></pre></div>
</div>
<!-- ======= START OF BOTTOM NAVBAR ====== -->
<div class="bottomNav"><a name="navbar.bottom">
<!-- -->
</a>
<div class="skipNav"><a href="#skip.navbar.bottom" title="Skip navigation links">Skip navigation links</a></div>
<a name="navbar.bottom.firstrow">
<!-- -->
</a>
<ul class="navList" title="Navigation">
<li><a href="../../../../../../overview-summary.html">Overview</a></li>
<li class="navBarCell1Rev">Package</li>
<li>Class</li>
<li><a href="package-use.html">Use</a></li>
<li><a href="package-tree.html">Tree</a></li>
<li><a href="../../../../../../deprecated-list.html">Deprecated</a></li>
<li><a href="../../../../../../index-all.html">Index</a></li>
<li><a href="../../../../../../help-doc.html">Help</a></li>
</ul>
<div class="aboutLanguage"><a href="http://edgent.incubator.apache.org">Apache Edgent (incubating)</a></div>
</div>
<div class="subNav">
<ul class="navList">
<li><a href="../../../../../../org/apache/edgent/samples/apps/mqtt/package-summary.html">Prev&nbsp;Package</a></li>
<li><a href="../../../../../../org/apache/edgent/samples/connectors/package-summary.html">Next&nbsp;Package</a></li>
</ul>
<ul class="navList">
<li><a href="../../../../../../index.html?org/apache/edgent/samples/apps/sensorAnalytics/package-summary.html" target="_top">Frames</a></li>
<li><a href="package-summary.html" target="_top">No&nbsp;Frames</a></li>
</ul>
<ul class="navList" id="allclasses_navbar_bottom">
<li><a href="../../../../../../allclasses-noframe.html">All&nbsp;Classes</a></li>
</ul>
<div>
<script type="text/javascript"><!--
allClassesLink = document.getElementById("allclasses_navbar_bottom");
if(window==top) {
allClassesLink.style.display = "block";
}
else {
allClassesLink.style.display = "none";
}
//-->
</script>
</div>
<a name="skip.navbar.bottom">
<!-- -->
</a></div>
<!-- ======== END OF BOTTOM NAVBAR ======= -->
<p class="legalCopy"><small>Copyright &#169; 2017 The Apache Software Foundation. All Rights Reserved - 4744f56-20170226-1707</small></p>
</body>
</html>