...
Code Block |
---|
https://[IP address or hostname]:[port]/video/ |
WILL BE DEPRECATED IN NEXT RELEASE, USE /channels
Returns stored video from the camera with the given camera number and options (start time, end time, length, framerate, and/or resolution). Note: Datetime values are formatted according to the ISO 8601 specification: YYYY-MM-DDTHH:MM:SS For example, 2012-12-05T13:40:27. For more information, see this article from the W3C W3.org: Date and Time Formats.
...
Query | URL | Description |
---|---|---|
ALL EVENTS | Returns the most recent events of any type. | |
MOTION EVENTS | Returns the most recent motion events. | |
FACE EVENTS | For VIP Appliances with the Facial Surveillance analytic enabled, returns the recent faces captured by the system. | |
GENERIC EVENTS | Returns event types that are not system defaults. This includes:
| |
ALERTS | Returns the most recent events that have triggered an alert. | |
SPECIFIC ALERT | https://[IP address or hostname]:8080/feed/alert/[alertname] | Returns the most recent events that triggered the alert named [alertname]. To return more than one alert name, separate the names with an ampersand (&). |
...
Code Block | ||
---|---|---|
| ||
<TimeRangePredicate name="TimeRange" isEnabled="True" id="" DistinctIndividualQueries="Fals e"> <FacetOperand reference="starttime" /> <ValueOperand type="System.DateTime" value="1/1/2000 11:00 PM" /> <ValueOperand type="System.DateTime" value="1/1/2000 1:00 AM" /> </TimeRangePredicate> |
Additional Predicates
While most queries are written using the and, or, and comparison predicates, there are a number of other predicates that are useful for more complex querying.
Disjoint Predicates
Disjoint and and Disjoint or are variants of the and and or predicates. The difference is in the way that they evaluate facets relative to each other. The regular and and or predicates treat multiple references to the same facet name as a reference to the same object in the database. This is very efficient, but sometimes can cause problems.
For example, when you want to query for a generic event which has two separate pieces of metadata (for example, teller ID and account number) set to specific number, the following and predicate will not work:
Code Block | ||
---|---|---|
| ||
<AndPredicate name="and" isEnabled="True" id="" DistinctIndividualQueries="False">
<!-- subclause 1, teller id = "870-19766" -->
<AndPredicate name="and" isEnabled="True" id="" DistinctIndividualQueries="False">
<ComparisonPredicate name="=" isEnabled="True" id="" DistinctIndividualQueries="False">
<FacetOperand reference="MetaDataElements.MetadataKey.Name" />
<Comparison operation="=" />
<ValueOperand type="System.String" value="Teller ID" />
</ComparisonPredicate>
<ComparisonPredicate name="=" isEnabled="True" id="" DistinctIndividualQueries="False">
<FacetOperand reference="MetaDataElements.MetadataStringValue.StringValue" />
<Comparison operation="=" />
<ValueOperand type="System.String" value="870-19766" />
</ComparisonPredicate>
</AndPredicate>
<!-- subclause 2, account number = "0076 5609 3817" -->
<AndPredicate name="and" isEnabled="True" id="" DistinctIndividualQueries="False">
<ComparisonPredicate name="=" isEnabled="True" id="" DistinctIndividualQueries="False">
<FacetOperand reference="MetaDataElements.MetadataKey.Name" />
<Comparison operation="=" />
<ValueOperand type="System.String" value="Account Number" />
</ComparisonPredicate>
<ComparisonPredicate name="=" isEnabled="True" id="" DistinctIndividualQueries="False">
<FacetOperand reference="MetaDataElements.MetadataStringValue.StringValue" />
<Comparison operation="=" />
<ValueOperand type="System.String" value="0076 5609 3817" />
</ComparisonPredicate>
</AndPredicate>
</AndPredicate> |
This does not work because MetaDataElements.MetadataKey.Name refers to the same database entry both times it's mentioned, and cannot equal both "Teller ID" and "Account Number" at the same time.
In order to make this work, we replace the top level with a disjoint and predicate:
Code Block |
---|
<DisjointAndPredicate name="disjointand" isEnabled="True" id="" DistinctIndividualQueries="
False">
<!-- subclause 1, teller id = "870-19766" -->
<AndPredicate name="and" isEnabled="True" id="" DistinctIndividualQueries="False">
… Same comparisons as above …
</AndPredicate>
<!-- subclause 2, account number = "0076 5609 3817" -->
<AndPredicate name="and" isEnabled="True" id="" DistinctIndividualQueries="False">
… Same comparisons as above …
</AndPredicate>
</DisjointAndPredicate> |
The disjoint or predicate works in the same fashion.
Info |
---|
The disjoint and and disjoint or predicates are much more expensive in terms of database load than the and and or predicates. For this reason, they should be avoided whenever possible. Often the use of an array value operand will have the same effect and be much more efficient. |
Not Predicate
The not predicate inverts the sense of a predicate included under it. For example, to find all events except those for cameras 1 and 2, use the following:
Code Block | ||
---|---|---|
| ||
<NotPredicate name="not" isEnabled="True" id="" DistinctIndividualQueries="False">
<ComparisonPredicate name="=" isEnabled="True" id="" DistinctIndividualQueries="False">
<FacetOperand reference="Channel.Id" />
<Comparison operation="=" />
<ArrayValueOperand>
<System.Long type="System.Long" value="1" />
<System.Long type="System.Long" value="2" />
</ArrayValueOperand>
</ComparisonPredicate>
</NotPredicate> |
Exists Predicate
The exists predicate determines if some item is in the database at all. For example, to find all events with notes, use this predicate:
Code Block | ||
---|---|---|
| ||
<ExistsPredicate name="exists" isEnabled="True" id="" DistinctIndividualQueries="False">
<FacetOperand reference="Notes.Id" />
</ExistsPredicate> |
The not exists predicate reverses the sense of exists and is identically structured. Always use this instead of creating a combination of not and exists. Not does not invert exists correctly because of the way that the SQL database works underneath.
Is Null Predicate
The Is Null predicate matches facets that exist, but are null in the database. It is structurally identical to the Exists predicate.
Time Range Predicate
The Time Range predicate allows you to retrieve events that occurred during a specified period during the day. It includes three operands: the facet to check, the beginning of the time range, and the end of the time range. If the end is earlier than the beginning, the time range is assumed to cross midnight. The time is passed as full date/times, but the date component is ignored.
Processing Returned Events
Upon receiving the POST request, 3VR system interprets the predicate, executes the query and sends a response of the summary of matching events in RSS 2.0 format:
Code Block | ||
---|---|---|
| ||
<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:media="http://search.yahoo.com/mrss/" xmlns:dc="http://purl.org/dc/
elements/1.1/">
<channel>
<title>3VR Events</title>
<link>https://<3vr-server>:8080/index.xml?allalerts=</link>
<description>Events matching the descriptions</description>
<pubDate>8/3/2007 4:50:43 PM</pubDate>
<lastBuildDate>8/3/2007 4:50:43PM</lastBuildDate>
<item>
<title>8/3/2007 4:47:15 PM - 8/3/2007 4:47:49 PM: Motion Event on Camera Camera 1</
title>
<link>http://<3vr-server>:80/event?id=1</link>
<description><img alt=https://<3vr-server>:8080/images/3 _ 8 _ 2007/23/eventtype
_ 1/0/1/images1.24.MFA src="https://<3vr-server>:8080/images/3 _ 8 _ 2007/23/eventtype
_ 1/0/1/images1.24.MFA" width=120 height=80><img alt=https://<3vr-server>:8080/
images/3 _ 8 _ 2007/23/eventtype _ 1/0/1/images1.25.MFA src="https://<3vr-server>:8080/images/
3 _ 8 _ 2007/23/eventtype _ 1/0/1/images1.25.MFA" width=120 height=80><img
alt=https://<3vr-server>:8080/images/3 _ 8 _ 2007/23/eventtype _ 1/0/1/images1.26.MFA
src="https://<3vr-server>:8080/images/3 _ 8 _ 2007/23/eventtype _ 1/0/1/images1.26.MFA" width=120
height=80></description>
<pubDate>4:50 PM</pubDate>
</item>
</channel>
</rss> |
Each <item> element represents a matching event.
Most of this response XML is intended to allow a browser to display reasonable output. As a programmer, the tag that you are most interested in is the <link> tag under <item>. Each <link> tag contains the URL for the detailed information about that event.
Since RSS 2.0 format complies with standard XML format, all standard methods for parsing XML, e.g. SAX, DOM, or simply parsing text, can be used to retrieve information from the XML document. Examples can be found in the section "Using Language-specific Libraries to Access the 3VR External Query API".
To retrieve the event information, use an HTTP GET command with the URL in the <link> element. The response XML can be processed using any standard XML parser, and has the following format:
Code Block | ||
---|---|---|
| ||
<ThreeVRExport version=version date=queryTime server="" ApplianceGuid=sourceGuid>
<ThreeVREventExport>
<EventCollectionExt>
<Events>
<Event> Property elements </Event>
</Events>
</EventCollectionExt>
</ThreeVREventExport>
</ThreeVRExport> |
There will always be only one <Event> element under <Events>. It is a structured object containing all information the 3VR system captured for that event, and all facets of that event will be stored in the elements or attributes.
Example 1: Facet "StartTime" is stored as an attribute in the <Event> tag.
Example 2: Facet "Channel" is stored in a <Channel> element under <Event>.
Example 3: The location of the profile image is an attribute in the <Profile> element under
<SpecializedEvent>, or "/ ThreeVRExport/ThreeVREventExport/EventCollectionExt/Events/Event/SpecializedEvent/FaceEvent/ProfileGroup/CanonicalProfile/Profile/@ImageLocation" as expressed in XPath.
A complete list of XPath for all facets can be found in the final section of this document.
The full XML response for a face event looks like this:
Code Block | ||
---|---|---|
| ||
<?xml version="1.0" encoding="utf-8"?>
<?xml-stylesheet type="text/xsl" href="/eventstylesheet.xsl"?>
<ThreeVRExport version="6.0" date="8/15/2007 10:52:32 AM" server="https://<3vr-server>:8080"
ApplianceGuid="30d53949-fe72-43b6-9429-8bb0e81ffde3">
<ThreeVREventExport>
<EventCollectionExt>
<Events>
<Event XmlReferenceId="0" StartTime="2007-07-18T16:50:53.6740000-07:00" _ Short
StartTime="7/18/2007 4:50:53 PM" EndTime="2007-07-18T16:50:55.3770000-07:00" _ ShortEnd-
Time="7/18/2007 4:50:55 PM" Status="Closed" Guid="9db1d70c-d3a7-499a-97af-c8ca9524e1b4">
<EventType XmlReferenceId="1" Name="Face" />
<Appliance XmlReferenceId="2" Name="Developer Workstation" HostAddress="<3vrserver>"
Guid="30d53949-fe72-43b6-9429-8bb0e81ffde3" />
<Channel XmlReferenceId="3" Name="Camera 1" DisplayNumber="1"
ChannelType="AnalogCamera" Description="" Identifier="analogcamera://1" />
<SpecializedEvent>
<FaceEvent XmlReferenceId="4" FaceEventType="Camera" MatchType="Indexed">
<ProfileGroup XmlReferenceId="5" Guid="1b0c21e5-1657-4f1f-bf1bebbc23f19391"
CreationDate="7/18/2007 4:50:53 PM" UseForAutoMatch="False" Version="67240452">
<CanonicalProfile>
<Profile XmlReferenceId="6" Guid="946d2ead-5461-4a47-9bf1-
634d3a139f29" Quality="0" AspectRatioAdjustment="1.10000002384186" NominalAspectRatio="2"
Width="704" Height="240" ImageWidth="704" ImageHeight="240" FaceLocationX="561.902709960938"
FaceLocationY="101.333190917969" FaceWidth="40.2184638977051" IsAnnotated="False"
ImageTimestamp="2007-07-18T16:50:54.4710000-07:00" _ ShortImageTimestamp="7/18/2007 4:50:54 PM"
ImageLocation="https://<3vr-server>:8080/images/18 _ 7 _ 2007/23/eventtype _ 2/0/1/images1.24.
MFA">
<Bits>…</Bits>
</Profile>
</CanonicalProfile>
<Profiles>
<Profile XmlReferenceId="6" IsReference="True" />
<Profile XmlReferenceId="7" Guid="511e23e4-d3d4-4f76-bc99-
801733b102a3" Quality="0" AspectRatioAdjustment="1.10000002384186" NominalAspectRatio="2"
Width="704" Height="240" ImageWidth="704" ImageHeight="240" FaceLocationX="588.512878417969"
FaceLocationY="119.292823791504" FaceWidth="37.9340286254883" IsAnnotated="False"
ImageTimestamp="2007-07-18T16:50:54.8770000-07:00" _ ShortImageTimestamp="7/18/2007 4:50:54 PM"
ImageLocation="https://<3vr-server>:8080/images/18 _ 7 _ 2007/23/eventtype _ 2/0/1/images1.25.
MFA">
<Bits>…</Bits>
</Profile>
<Profile XmlReferenceId="8" Guid="e763ef30-2315-4917-9d50-
70447662a0a1" Qual ity="0" AspectRatioAdjustment="1.10000002384186" NominalAspectRatio="2"
Width="704" Height="240" ImageWidth="704" ImageHeight="240" FaceLocationX="573.310546875"
FaceLocationY="101.27188873291" FaceWidth="40.6226844787598" IsAnnotated="False"
ImageTimestamp="2007-07-18T16:50:54.5800000-07:00" _ ShortImageTimestamp="7/18/2007 4:50:54 PM"
ImageLocation="https://<3vr-server>:8080/images/18 _ 7 _ 2007/23/eventtype _ 2/0/1/images1.26.
MFA">
<Bits>…</Bits>
</Profile>
</Profiles>
</ProfileGroup>
<BaseEvent>
<Event XmlReferenceId="0" IsReference="True" />
</BaseEvent>
<Frames>
<FaceFrame XmlReferenceId="9" IsSubGroupFrame="False" FaceConfidence="3.91948986053467" FaceLocationX="561.902709960938" FaceLocationY="101.333190917969"
FaceQuality="0" FaceWidth="40.2184638977051" FirstEyeConfidence="3.95001864433289" First-
EyeLocationX="540.107666015625" FirstEyeLocationY="100.637741088867" SecondEyeConfidence="
3.49672865867615" SecondEyeLocationX="580.898864746094" SecondEyeLocationY="
100.739883422852">
<Picture XmlReferenceId="10" TimeStamp="2007-07-
18T16:50:54.4710000-07:00" _ ShortTimeStamp="7/18/2007 4:50:54 PM" AspectRatioAdjustment="
1.10000002384186" NominalAspectRatio="2" Width="704" Height="240" ImageWidth="704" ImageHeight="
240" IsAnnotated="False" FilePath="https://<3vr-server>:8080/images/18 _ 7 _ 2007/23/
eventtype _ 2/0/1/images1.21.MFA" />
</FaceFrame>
<FaceFrame XmlReferenceId="11" IsSubGroupFrame="False" FaceConfidence="
3.1991331577301" FaceLocationX="573.310546875" FaceLocationY="101.27188873291"
FaceQuality="0" FaceWidth="40.6226844787598" FirstEyeConfidence="3.51949620246887"
FirstEyeLocationX="550.122863769531" FirstEyeLocationY="99.4405822753906" SecondEye-
Confidence="2.99968218803406" SecondEyeLocationX="592.0732421875" SecondEyeLocationY="
99.338264465332">
<Picture XmlReferenceId="12" TimeStamp="2007-07-
18T16:50:54.5800000-07:00" _ ShortTimeStamp="7/18/2007 4:50:54 PM" AspectRatioAdjustment="
1.10000002384186" NominalAspectRatio="2" Width="704" Height="240" ImageWidth="704" ImageHeight="
240" IsAnnotated="False" FilePath="https://<3vr-server>:8080/images/18 _ 7 _ 2007/23/
eventtype _ 2/0/1/images1.23.MFA" />
</FaceFrame>
<FaceFrame XmlReferenceId="13" IsSubGroupFrame="False" FaceConfidence="
3.20546126365662" FaceLocationX="588.512878417969" FaceLocationY="119.292823791504"
FaceQuality="0" FaceWidth="37.9340286254883" FirstEyeConfidence="2.94460487365723" First-
EyeLocationX="563.047180175781" FirstEyeLocationY="120.273956298828" SecondEyeConfidence="
3.68825888633728" SecondEyeLocationX="607.244323730469" SecondEyeLocationY="
119.276374816895">
<Picture XmlReferenceId="14" TimeStamp="2007-07-
18T16:50:54.8770000-07:00" _ ShortTimeStamp="7/18/2007 4:50:54 PM" AspectRatioAdjustment="
1.10000002384186" NominalAspectRatio="2" Width="704" Height="240" ImageWidth="704" ImageHeight="
240" IsAnnotated="False" FilePath="https://<3vr-server>:8080/images/18 _ 7 _ 2007/23/
eventtype _ 2/0/1/images1.22.MFA" />
</FaceFrame>
</Frames>
<Videos>
<Video XmlReferenceId="15" StartTime="2007-07-18T16:50:27.5800000-07:00"
_ ShortStartTime="7/18/2007 4:50:27 PM" EndTime="2007-07-18T16:50:59.6110000-07:00" _ Short-
EndTime="7/18/2007 4:50:59 PM" ChannelId="1" PixelAspectRatioAdjustment="1.10000002384186"
PixelAspectRatioNominal="1" Width="352" Height="240" VideoFormat="HikvisionH264"
FilePath="https://<3vr-server>:8080/videos/18 _ 7 _ 2007/23/videos/0/1/17.mpg" />
</Videos>
</FaceEvent>
</SpecializedEvent>
<TriggeredAlerts />
<MetadataElements />
</Event>
</Events>
</EventCollectionExt>
</ThreeVREventExport>
</ThreeVRExport> |
Using Language Specific Libraries to Access the 3VR External Query API
3VR provides libraries and samples in various programming languages for easily using the 3VR Query API. You only need to supply a few essential elements to generate query XML. We also provide utility methods to execute the query using POST, return the XML including event details using GET, and parse the XML response.
Language-specific libraries are included (with source code) in the 3VR web services SDK. The 3VR External Query API currently has language support for client programs written in Java and Python. Support for additional languages will be added in the future. Of course, it is possible to directly access the query API from any programming language using XML/HTTP.
3VR External Query API Support for Java Programming
...
To use 3VR query Java API, add threeVRQuery.jar to your Java project library and import any necessary packages in your Java program.
Code Block | ||
---|---|---|
| ||
import com.threeVR.predicate.* |
Now you will be able to use predicates to construct the query XML.
Code Block | ||
---|---|---|
| ||
// Events that triggered Alert 'My Alert'
Predicate pred = new LikeP("TriggeredAlerts.Alert.Name", "My Alert");
String queryxml = pred.ToXmlString();
// Events that triggered alerts
ExistsPredicate existPred = new ExistsPredicate("TriggeredAlerts.Alert.Id");
queryxml = existPred.ToXmlString();
// Similarity Search
AndP pred = new AndP(new Predicate[] {
new EqP("eventtype", new Integer(2)), new GeP("starttime", starttime),
new LeP("starttime", endtime),
new SimilarityP(null, personids, 0.8f, starttime,endtime)
});
queryXml = pred.ToXmlString(); |
Once you have generated the query xml, you can perform a POST operation to http://[IP or hostname]/rss to return an XML response which contains a summary of matching events. In the Java library we provide utility methods for performing the POST operation. Here's an example for using that method to easily obtain response XML:
Code Block |
---|
// POST queryXml to https://<3vr-server:port>
String response = Utilities.query(queryXml, "3vr-server", port); |
After obtaining response XML for the matching event summary, we can use any standard XML library to process it. Here is an example using JAXP. The Java API for XML Processing (JAXP) is a library that enables applications to parse and transform XML documents independent of a particular XML processing implementation. We can use JAXP6 to parse RSS formatted events summary response.
Code Block | ||
---|---|---|
| ||
//JAXP example
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder parser = factory.newDocumentBuilder();
Document xmldoc = parser.parse(new InputSource(new StringReader(response)));
NodeList items = xmldoc.getElementsByTagName("item");
for (int i = 0; i < items.getLength(); i++) {
Node item = items.item(i);
NodeList children = item.getChildNodes();
for (int j = 0; j < children.getLength(); j++) {
if (children.item(j).getNodeName().equals("link")) {
String link = children.item(j).getTextContent(); //proceed with link
}
}
} |
We also provide examples for processing the response XML by parsing text or using DOM. Examples can be found in Utilities.java.
Code Block | ||
---|---|---|
| ||
// Parsing text
public static void processResultsSummary _ Text(String response){…}
// DOM processing
public static void processResultsSummary _ DOM(String response){…} |
After processing event summary XML, we can use the content of the <link> element to perform a GET operation and retrieve detail for events of interest. We provide a utility method in Utitlities.java for this purpose.