 <blockquote> <p>Is node traversal far better (in a multilevel datetime index) in term of performance than dealing with indexed properties for dates in this case?</p> </blockquote> <p>No, indexed properties for dates is more performant than traversals for this type of data structure.</p> <p>Here is detailed example of using a hybrid approach. Consider the following subgraph, where the elipses indicate a continuing pattern in the graph.</p> <p><img src="https://i.stack.imgur.com/896SD.png" alt="Multilevel Calendar Index"></p> <p>Please take a look at <a href="https://gist.github.com/kbastani/8519557" rel="nofollow noreferrer">https://gist.github.com/kbastani/8519557</a> for the full calendar Cypher scripts that get or create (merge) a multilevel datetime index. This data structure allows you to traverse from one date to another date to get a range of events for a time series. A combination of both indexed property matching and traversals is the best approach, and is performant when modeled correctly.</p> <p><img src="https://i.stack.imgur.com/Pc1iB.png" alt="Example Data Model for Time"></p> <p>For example, consider the following Cypher query:</p> <pre><code>// What staff have been on the floor for 80 minutes or more on a specific day? WITH { day: 18, month: 1, year: 2014 } as dayMap // The dayMap field acts as a parameter for this script MATCH (day:Day { day: dayMap.day, month: dayMap.month, year: dayMap.year }), (day)-[:FIRST|NEXT*]-&gt;(hours:Hour), (hours)&lt;-[:BEGINS]-(shift:Event), (shift)&lt;-[:WORKED]-(employee:Employee) WITH shift, employee ORDER BY shift.timestamp DESC WITH employee, head(collect(shift)) as shift MATCH (shift)&lt;-[:CONTINUE*]-(shifts) WITH employee.firstname as first_name, employee.lastname as last_name, SUM(shift.interval) as time_on_floor // Only return results for staff on the floor more than 80 minutes WHERE time_on_floor &gt;= 80 RETURN first_name, last_name, time_on_floor </code></pre> <p>In this query we are asking the database "What staff have been on the floor for 80 continuous minutes or more on a specific day?" where shifts are broken up into 20 minute continuous intervals pointing to the next one in the series as CONTINUE or BREAK. </p> <p>First you start with matching the day using the indexed properties. Then you scan the day's hours for connected events by traversing the datetime multilevel index. Then reverse the order of the events to get the most recent event in the series. Then traverse until a "BREAK" relationship is encountered. Finally, apply the condition of time_on_floor being greater or equal to 80 minutes.</p>