Time tracking script

Published with Share Note 🔸 Part of Obsidian guides

Here’s what I do, maybe there’s something useful here.

I track my time in a section in my daily note, in this format. I use Templater to insert the timestamps for me:

## đź•” Time tracking
- 07:30-10:56 Some stuff
- 10:56-11:23 Another task, did some things
- 12:34-13:30 Third project

Then I have a master time tracking note which sums them all up for me using Dataview, in hours-per-week/day:

const tracked = {}
dv.pages('"Daily/Notes"').file.lists
  .where(x => x.section.subpath === "đź•” Time tracking").array()
  .forEach(x => {
    // Find the start/end times for each bullet point
    const times = x.text.match(/^(\d{2}:\d{2})-(\d{2}:\d{2})/)
    if (times) {
      const start = moment(times[1], 'HH:mm')
      const end = moment(times[2], 'HH:mm')
      const minutes = moment.duration(end.diff(start)).asMinutes()
      const date = x.path.match(/(\d{4}-\d{2}-\d{2})/)[1]
      const week = moment(date).format('YYYY, [Week] WW')
      if (!tracked[week]) tracked[week] = {}
      if (tracked[week][date]) {
        tracked[week][date].minutes += minutes
      } else {
        tracked[week][date] = {
          path: x.path,
          minutes: minutes
        }
      }
    }
  })
 
const hours = minutes => (minutes / 60).toFixed(1)
 
const table = []
Object.keys(tracked).sort((a, b) => b.localeCompare(a))
  .forEach(weekDate => {
    // Push weekly value
    const week = tracked[weekDate]
    const weekTime = Object.values(week).reduce((prev, curr) => prev + curr.minutes, 0)
    table.push([weekDate, '**' + hours(weekTime) + '**'])
 
    // Push daily values
    Object.keys(week).sort((a, b) => b.localeCompare(a))
      .forEach(date => {
        const link = `– [[${week[date].path}#🕔 Time tracking|${moment(date).format('dddd D MMMM')}]]`
        table.push([link, '– ' + hours(week[date].minutes)])
      })
  })
 
dv.table(['Date', 'Hours'], table)

The summary table looks like this, with links back to each day:


Mentioned: