Introduction

The WakaTime API follows common REST conventions. This means you should use GET requests to retrieve data and POST, PUT, or PATCH requests to modify data. All API requests must be done over HTTPS.

Every response will be a JSON object, which is a key-value hash. Data for a resource will be returned in the key named data. Errors will be returned in the key named errors or error.

HTTP response codes indicate the status of your request:

All API resources have the url prefix https://wakatime.com/api/v1/.

When using the WakaTime trademark or logo in your application, please follow our usage guidelines.

Security

Do NOT use the API with your secret key on a public website. Instead, create an embeddable chart that's safe to share publicly. Choose the JSON format to securely access your coding activity with JavaScript:

Embeddable SVG Charts and JSON

Authentication

OAuth 2.0 Endpoints

Create an app to get an OAuth 2.0 client token.

The OAuth 2.0 provider endpoints are:

  • https://wakatime.com/oauth/authorize - Redirect your users here to request permission to access their account. Required url arguments are client_id, response_type of code or token, redirect_uri, scope. Optional parameters are state and force_approve.
  • https://wakatime.com/oauth/token - Make a server-side POST request here to get the secret access token. Required x-www-form-urlencoded data is client_id, client_secret, redirect_uri must be the same url used in authorize step, grant_type of authorization_code, and the code received from the authorize step.

For information about using these endpoints, see RFC6749 OAuth 2.0.

Using Access Token

After getting the bearer (access) token from https://wakatime.com/oauth/token, you can now make authenticated api calls using the Authorization request header (RFC 6750).

For example, if your user's access token is sec_12345, you would add this header to your request:
Authorization: Bearer sec_12345.

Alternatively, you can authenticate with url args named access_token, or just token and app_secret, client_secret, or just secret.

Using the Refresh Token

You should always get a refresh_token from the /oauth/token response. The refresh_token can be used when your access_token has expired, to re-authorize without having to prompt the user.

To use the refresh_token, make a POST request to https://wakatime.com/oauth/token to get a new secret access token. Required x-www-form-urlencoded data is client_id, client_secret, redirect_uri must be the same url used in authorize step, grant_type of refresh_token, and the refresh_token received from a previous token response.

Available Scopes

Scopes are sent to the authorize url as a comma separated list.

  • email - access user’s email and identity information.
  • read_logged_time - access user’s coding activity and other stats.
  • write_logged_time - modify user’s coding activity.
  • read_stats - access user’s languages, editors, and operating systems used.
  • read_orgs - access user’s organizations, and coding activity for dashboard members.
  • read_private_leaderboards - access user’s private leaderboards.
  • write_private_leaderboards - modify user’s private leaderboards, including adding/removing members when current user had Admin or Owner role.

Example

OAuth 2.0 authentication flow using rauth (Python):

#!/usr/bin/env python

import hashlib
import os
import sys
from rauth import OAuth2Service

if sys.version_info[0] == 3:
    raw_input = input

client_id = raw_input('Enter your App Id: ')
secret = raw_input('Enter your App Secret: ')

service = OAuth2Service(
    client_id=client_id,  # your App ID from https://wakatime.com/apps
    client_secret=secret,  # your App Secret from https://wakatime.com/apps
    name='wakatime',
    authorize_url='https://wakatime.com/oauth/authorize',
    access_token_url='https://wakatime.com/oauth/token',
    base_url='https://wakatime.com/api/v1/')

redirect_uri = 'https://wakatime.com/oauth/test'
state = hashlib.sha1(os.urandom(40)).hexdigest()
params = {'scope': 'email,read_stats',
          'response_type': 'code',
          'state': state,
          'redirect_uri': redirect_uri}

url = service.get_authorize_url(**params)

print('**** Visit this url in your browser ****'.format(url=url))
print('*' * 80)
print(url)
print('*' * 80)
print('**** After clicking Authorize, paste code here and press Enter ****')
code = raw_input('Enter code from url: ')

# Make sure returned state has not changed for security reasons, and exchange
# code for an Access Token.
headers = {'Accept': 'application/x-www-form-urlencoded'}
print('Getting an access token...')
session = service.get_auth_session(headers=headers,
                                   data={'code': code,
                                         'grant_type': 'authorization_code',
                                         'redirect_uri': redirect_uri})

print('Getting current user from API...')
user = session.get('users/current').json()
print('Authenticated via OAuth as {0}'.format(user['data']['email']))
print("Getting user's coding stats from API...")
stats = session.get('users/current/stats')
print(stats.text)

400 Error (Invalid redirect_uri: Not valid for this client.)

If you see this error when running the example, add https://wakatime.com/oauth/test as an authorized redirect url in your App's settings.

Using API Key

Most apps should use OAuth, but you can also authenticate to the WakaTime API using your secret API key .

Using HTTP Basic Auth pass your API key base64 encoded in the Authorization header. Don't forget to prepend Basic to your api key after base64 encoding it.

For example, when using HTTP Basic Auth with an api key of 12345 you should add this header to your request:
Authorization: Basic MTIzNDU=

That’s because when you decode the base64 string "MTIzNDU=" you get "12345".

Alternatively, you can pass your api key as a query parameter in your request like ?api_key=XXXX.

Do NOT use your API Key on a public website. Instead, use embeddable charts and JSON.

Writing your own plugin

WakaTime plugins are extensions that run inside your text editor or IDE sending usage stats, called heartbeats, to your WakaTime Dashboard. All official WakaTime plugins are open source on GitHub.

When building your own editor plugin, use our Creating a WakaTime plugin guide.

Embedding Charts & JSON

Want to share your WakaTime stats? Use the embeddable charts and JSON to safely embed your coding activity on a public website without leaking your secret api key. Select the JSON format for access to your coding stats in JavaScript. We don’t support Cross-Origin Resource Sharing (CORS) because the only way to access your coding stats safely in public JavaScript is with embeddable JSON. Embeddable JSON does support JSONP. Embeddable charts and JSON use a one-time unique url and can be retracted to prevent future access to your coding stats.

Never use the WakaTime API from a public website, except for embeddables. Using your secret api key in client-side JavaScript gives everyone on the internet full access to your WakaTime account.

Commits

GET /api/v1/users/:user/projects/:project/commits

GET /api/v1/users/current/projects/:project/commits

Description

List of commits for a WakaTime project showing the time spent coding in each commit.

URL Parameters

author - String - optional - Filter commits to only those authored by the given username.

page - Integer - optional - Page number of commits.

Scope Required

read_logged_time

Example Response

Response Code: 200

{
  "commits": [
    {
      "author_avatar_url": <string: url of author's avatar image>
      "author_date": <datetime: time when commit was authored in ISO 8601 format>,
      "author_email": <string: email address of author>,
      "author_html_url": <string: link to author's profile on GitHub, Bitbucket, GitLab, etc>,
      "author_name": <string: name of author>,
      "author_url": <string: api url for author's profile>,
      "author_username": <string: author's username>,
      "committer_avatar_url": <string: url of committer's avatar image>,
      "committer_date": <datetime: commit time in ISO 8601 format>,
      "committer_email": <string: email address of committer>,
      "committer_html_url": <string: link to committer's profile on GitHub, Bitbucket, GitLab, etc>,
      "committer_name": <string: name of committer>,
      "committer_url": <string: api url for committer's profile>,
      "committer_username": <string: committer's username>,
      "created_at": <datetime: time commit was synced in ISO 8601 format>,
      "hash": <string: revision control hash of this commit>,
      "html_url": <string: link to an html page with details about current commit>,
      "human_readable_total": <string: time coded in editor for this commit>,
      "human_readable_total_with_seconds": <string: time coded in editor for this commit>,
      "id": <string: unique id of commit>,
      "message": <string: author's description of this commit>,
      "ref": <string: refs/heads/master>,
      "total_seconds": <float: time coded in editor for this commit>,
      "truncated_hash": <string: truncated revision control hash of this commit>,
      "url": <string: api url with details about current commit>,
    }, …
  ],
  "author": <string: current author or null if showing commits from all authors>,
  "next_page": <integer: next page number or null if last page>
  "next_page_url": <string: url for next page or null if last page>
  "page": <integer: current page number>
  "prev_page": <integer: previous page number or null if first page>
  "prev_page_url": <string: url for previous page or null if first page>
  "project": {
    "id": <string: unique id of project>,
    "name": <string: project name>,
    "privacy": <string: project privacy setting>,
    "repository": {
      "default_branch": <string: default branch if given for this repo>,
      "description": <string: remote repository description>,
      "fork_count": <integer: number of repo forks if available>
      "full_name": <string: username and repo name, ex: wakatime/wakadump>,
      "homepage": <string: homepage of repository>,
      "html_url": <string: html url for repository>,
      "id": <string: unique id of repository>,
      "is_fork": <boolean: whether this repo is a fork or original>,
      "is_private": <boolean: whether this repo is private or public>,
      "last_synced_at": <datetime: last time this repo was synced with remote provider iSO 8601 format>,
      "name": <string: repository name>,
      "provider": <string: remote provider of repository, ex: github>,
      "star_count": <integer: number of repo stars if available>
      "url": <string: api url of remote repository>,
      "watch_count": <integer: number of watchers of repo if available>,
    }
  },
  "status": <string: project's sync status>,
  "total": <integer: number of commits available>,
  "total_pages": <integer: number of pages available>,
}

Durations

GET /api/v1/users/:user/durations

GET /api/v1/users/current/durations

Description

A user's coding activity for the given day as an array of durations.

URL Parameters

date - Date - required - Requested day; Durations will be returned from 12am until 11:59pm in user's timezone for this day.

project - String - optional - Only show durations for this project.

branches - String - optional - Only show durations for these branches; comma separated list of branch names.

Scope Required

read_logged_time

Example Response

Response Code: 200

{
  "data": [
    {
      "project": <string: project name>,
      "time": <float: start of this duration as ISO 8601 UTC datetime; numbers after decimal point are fractions of a second>,
      "duration": <float: length of time of this duration in seconds>
    }, …
  ],
  "branches": <list of strings: branches included in this response>,
  "start": <integer: start of time range as ISO 8601 UTC datetime>,
  "end": <integer: end of time range as ISO 8601 UTC datetime>,
  "timezone": <string: timezone used for this request in Olson Country/Region format>
}

Goals

GET /api/v1/users/:user/goals

GET /api/v1/users/current/goals

Description

List a user’s goals.

URL Parameters

Scope Required

read_logged_time

Example Response

Response Code: 200

{
  "data": [
    {
      "average_status": <string: "fail" when there are more failure days or weeks than success, otherwise "success">,
      "chart_data": {
        "actual_seconds": <float: number of seconds coded during this delta period>,
        "actual_seconds_text": <string: human readable time coded during this delta period>,
        "goal_seconds": <integer: number of seconds required to meet goal for this delta period>,
        "goal_seconds_text": <string: human readable coding time required to meet goal for this delta period>,
        "range": {
          "date": <string: current time range as Date string in YEAR-MONTH-DAY format (only available when delta is "day")>,
          "end": <integer: end of current time range as ISO 8601 UTC datetime>,
          "start": <integer: start of current time range as ISO 8601 UTC datetime>,
          "text": <string: current range in human-readable format relative to the current day>,
          "timezone": <string: timezone used in Olson Country/Region format>
        },
        "range_status": <string: either "success", "fail", "pending", or "ignored">
        "range_status_reason": <string: an explanation for why this delta period passed or failed>
      },
      "cumulative_status": <string: status over all delta periods, either "success", "fail", or "ignored">,
      "delta": <string: goal step duration; either "day" or "week">,
      "id": <string: unique id of goal>,
      "ignore_days": <list of strings: goal status set to "ignored" instead of "failed" for these weekdsays, when delta is "day">,
      "improve_by_percent": <float: percent goal should increase each delta>,
      "is_enabled": <boolean: whether this goal is enabled or disabled>,
      "languages": <list of strings: languages for this goal>,
      "projects": <list of strings: projects for this goal>,
      "range_text": <string: complete range of this goal for all delta periods in human-readable format>,
      "seconds": <integer: goal amount>,
      "status": <string: most recent day or week range status; can be "success", "fail", "ignored", or "pending">,
      "subscribers": [
        {
          "email": <string: email address of this subscriber, if public>,
          "email_frequency": <string: how often this subscriber receives emails about this goal>,
          "full_name": <string: name of this subscriber, if public>,
          "user_id": <string: unique id of this subscriber>,
          "username": <string: username of this subscriber, if defined>
        }, …
      ],
      "title": <string: human readable title for this goal>,
      "type": <string: type of goal>
    }, …
  ],
  "total": <integer: number of goals>,
  "total_pages": <integer: number of pages>,
}

Heartbeats

POST /api/v1/users/:user/heartbeats

POST /api/v1/users/current/heartbeats

Description

Creates a heartbeat representing activity for a user.

URL Parameters

Scope Required

write_logged_time

JSON POST Data

{
  "entity": <string: entity heartbeat is logging time against, such as an absolute file path or domain>,
  "type": <string: type of entity; can be file, app, or domain>,
  "category": <string: category for this activity; can be coding, building, indexing, debugging, browsing, running tests, writing tests, manual testing, code reviewing, or designing>,
  "time": <float: UNIX epoch timestamp; numbers after decimal point are fractions of a second>,
  "project": <string: project name (optional)>,
  "branch": <string: branch name (optional)>,
  "language": <string: language name (optional)>,
  "dependencies": <string: comma separated list of dependencies detected from entity file (optional)>,
  "lines": <integer: total number of lines in the entity (when entity type is file)>,
  "lineno": <integer: current line row number of cursor (optional)>,
  "cursorpos": <integer: current cursor column position (optional)>,
  "is_write": <boolean: whether this heartbeat was triggered from writing to a file (optional)>,
}

Example Response

Response Code: 201

{
  "data": {
    "id": <string: unique id of newly created heartbeat>,
    "entity": <string: entity heartbeat is logging time against, such as an absolute file path or domain>,
    "type": <string: type of entity; can be file, app, or domain>,
    "time": <float: UNIX epoch timestamp; numbers after decimal point are fractions of a second>,
  }
}


GET /api/v1/users/:user/heartbeats

GET /api/v1/users/current/heartbeats

Description

A user's heartbeats sent from plugins for the given day as an array.

URL Parameters

date - Date - required - Requested day; Heartbeats will be returned from 12am until 11:59pm in user's timezone for this day.

Scope Required

read_logged_time

Example Response

Response Code: 200

{
  "data": [
    {
      "entity": <string: entity heartbeat is logging time against, such as an absolute file path or domain>,
      "type": <string: type of entity; can be file, app, or domain>,
      "category": <string: category for this activity; can be coding, building, indexing, debugging, browsing, running tests, writing tests, manual testing, code reviewing, or designing>,
      "time": <float: UNIX epoch timestamp; numbers after decimal point are fractions of a second>,
      "project": <string: project name (optional)>,
      "branch": <string: branch name (optional)>,
      "language": <string: language name (optional)>,
      "dependencies": <string: optional comma separated list of dependencies detected from entity file (optional)>,
      "machine_name_id": <string: unique id of the machine which generated this coding activity>,
      "lines": <integer: total number of lines in the entity (when entity type is file)>,
      "lineno": <integer: current line row number of cursor (optional)>,
      "cursorpos": <integer: current cursor column position (optional)>,
      "is_write": <boolean: whether this heartbeat was triggered from writing to a file>,
    }, …
  ],
  "start": <integer: start of time range as ISO 8601 UTC datetime>,
  "end": <integer: end of time range as ISO 8601 UTC datetime>,
  "timezone": <string: timezone used for this request in Olson Country/Region format>
}

Leaders

GET /api/v1/leaders

Description

List of users ranked by coding activity in descending order. Same as the public leaderboards.

URL Parameters

language - String - optional - Filter leaders by a specific language.

page - Integer - optional - Page number of leaderboard.

Example Response

Response Code: 200

{
  "current_user": {
    "rank": <integer: rank of the currently authorized user>,
    "running_total": {
      "total_seconds": <float: total coding activity for this user as seconds>,
      "human_readable_total": <string: total coding activity for this user as human readable string>,
      "daily_average": <float: daily average for this user as seconds>,
      "human_readable_daily_average": <string: daily average for this user as human readable string>,
      "languages": [
        {
          "name": <string: language name>,
          "total_seconds": <float: total seconds user has logged in this language>,
        }, …
      ],
    },
    "user": {
      "id": <string: unique id of user>,
      "email": <string: email address of user, if public>,
      "username": <string: users public username>,
      "full_name": <string: full name of user>,
      "display_name": <string: display name of this user taken from full_name or @username. Defaults to 'Anonymous User'>,
      "website": <string: website of user>,
      "human_readable_website": <string: website of user without url scheme>,
      "location": <string: location of user>,
      "email_public": <boolean: whether this user's email should be shown publicly on leader boards>,
      "photo_public": <boolean: whether this user's photo should be shown publicly on leader boards>,
    },
  },
  "data": [
    {
      "rank": <integer: rank of this leader>,
      "running_total": {
        "total_seconds": <float: total coding activity for this user as seconds>,
        "human_readable_total": <string: total coding activity for this user as human readable string>,
        "daily_average": <float: daily average for this user as seconds>,
        "human_readable_daily_average": <string: daily average for this user as human readable string>,
        "languages": [
          {
            "name": <string: language name>,
            "total_seconds": <float: total seconds user has logged in this language>,
          }, …
        ],
      },
      "user": {
        "id": <string: unique id of user>,
        "email": <string: email address of user, if public>,
        "username": <string: users public username>,
        "full_name": <string: full name of user>,
        "display_name": <string: display name of this user taken from full_name or @username. Defaults to 'Anonymous User'>,
        "website": <string: website of user>,
        "human_readable_website": <string: website of user without url scheme>,
        "location": <string: location of user>,
        "email_public": <boolean: whether this user's email should be shown publicly on leader boards>,
        "photo_public": <boolean: whether this user's photo should be shown publicly on leader boards>,
      },
    }, …
  ],
  "page": <integer: current page number>
  "total_pages": <integer: number of pages available>,
  "range": {
    "start_date": <integer: start of this range as ISO 8601 UTC datetime>,
    "start_text": <string: start of range in human-readable format relative to the current day>,
    "end_date": <integer: end of range as ISO 8601 UTC datetime>,
    "end_text": <string: end of range in human-readable format relative to the current day>,
    "name": <string: time range of this leaderboard>,
    "text": <string: time range in human-readable format relative to the current day>,
  }
  "language": <string: language of this leaderboard>,
  "modified_at": <datetime: time when this leaderboard was last updated in ISO 8601 format>
  "timeout": <integer: timeout setting in minutes used by this leaderboard>,
  "writes_only": <boolean: writes_only setting used by this leaderboard>,
}

Try it out

Meta

GET /api/v1/meta

Description

Information about WakaTime, such as a list of public ip addresses used by WakaTime servers.

URL Parameters

Example Response

Response Code: 200

{
  "data": {
    "ips": {
      "api": <list of strings: ip addresses used by WakaTime api servers>,
      "website": <list of strings: ip addresses used by WakaTime website servers>,
      "worker": <list of strings: ip addresses used by WakaTime background worker servers>
    },
  },
}

Try it out

Org Dashboard Member Durations

GET /api/v1/users/:user/orgs/:org/dashboards/:dashboard/members/:member/durations

GET /api/v1/users/current/orgs/:orgs/dashboards/:dashboard/members/:member/durations

Description

A dashboard member's coding activity for the given day as an array of durations.

URL Parameters

date - Date - required - Date in YYYY-MM-DD format.

project - String - optional - Only show durations for this project.

branches - String - optional - Only show durations for these branches; comma separated list of branch names.

Scope Required

read_orgs

Example Response

Response Code: 200

{
  "data": [
    {
      "project": <string: project name>,
      "time": <float: start of this duration as ISO 8601 UTC datetime; numbers after decimal point are fractions of a second>,
      "duration": <float: length of time of this duration in seconds>
    }, …
  ],
  "start": <integer: start of time range as ISO 8601 UTC datetime>,
  "end": <integer: end of time range as ISO 8601 UTC datetime>,
  "timezone": <string: timezone used for this request in Olson Country/Region format>
}

Org Dashboard Member Summaries

GET /api/v1/users/:user/orgs/:org/dashboards/:dashboard/members/:member/summaries

GET /api/v1/users/current/orgs/:org/dashboards/:dashboard/members/:member/summaries

Description

An organization dashboard member’s coding activity for the given time range as an array of summaries segmented by day.

URL Parameters

start - Date - required - Start date of the time range.

end - Date - required - End date of the time range.

project - String - optional - Only show time logged to this project.

branches - String - optional - Only show coding activity for these branches; comma separated list of branch names.

Scope Required

read_orgs

Example Response

Response Code: 200

{
  "data": [
    {
      "grand_total": {
        "digital": <string: total coding activity in digital clock format>,
        "hours": <integer: hours portion of coding activity>,
        "minutes": <integer: minutes portion of coding activity>,
        "text": <string: total coding activity in human readable format>,
        "total_seconds": <float: total coding activity as seconds>
      },
      "projects": [
        {
          "name": <string: project name>,
          "total_seconds": <float: total coding activity as seconds>,
          "percent": <float: percent of time spent in this project>,
          "digital": <string: total coding activity for this project in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this project>,
          "minutes": <integer: minutes portion of coding activity for this project>
        }, …
      ],
      "languages": [
        {
          "name": <string: language name>,
          "total_seconds": <float: total coding activity spent in this language as seconds>,
          "percent": <float: percent of time spent in this language>,
          "digital": <string: total coding activity for this language in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this language>,
          "minutes": <integer: minutes portion of coding activity for this language>,
          "seconds": <integer: seconds portion of coding activity for this language>
        }, …
      ],
      "editors": [
        {
          "name": <string: editor name>,
          "total_seconds": <float: total coding activity spent in this editor as seconds>,
          "percent": <float: percent of time spent in this editor>,
          "digital": <string: total coding activity for this editor in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this editor>,
          "minutes": <integer: minutes portion of coding activity for this editor>,
          "seconds": <integer: seconds portion of coding activity for this editor>
        }, …
      ],
      "operating_systems": [
        {
          "name": <string: os name>,
          "total_seconds": <float: total coding activity spent in this os as seconds>,
          "percent": <float: percent of time spent in this os>,
          "digital": <string: total coding activity for this os in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this os>,
          "minutes": <integer: minutes portion of coding activity for this os>,
          "seconds": <integer: seconds portion of coding activity for this os>
        }, …
      ],
      "branches": [ // included only when project url parameter used
        {
          "name": <string: branch name>,
          "total_seconds": <float: total coding activity spent in this branch as seconds>,
          "percent": <float: percent of time spent in this branch>,
          "digital": <string: total coding activity for this branch in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this branch>,
          "minutes": <integer: minutes portion of coding activity for this branch>,
          "seconds": <integer: seconds portion of coding activity for this branch>
        }, …
      ],
      "entities": [ // included only when project url parameter used
        {
          "name": <string: entity name>,
          "total_seconds": <float: total coding activity spent in this entity as seconds>,
          "percent": <float: percent of time spent in this entity>,
          "digital": <string: total coding activity for this entity in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this entity>,
          "minutes": <integer: minutes portion of coding activity for this entity>,
          "seconds": <integer: seconds portion of coding activity for this entity>
        }, …
      ],
      "range": {
        "date": <string: this day as Date string in YEAR-MONTH-DAY format>,
        "start": <integer: start of this day as ISO 8601 UTC datetime>,
        "end": <integer: end of this day as ISO 8601 UTC datetime>,
        "text": <string: this day in human-readable format relative to the current day>,
        "timezone": <string: timezone used in Olson Country/Region format>
      }
    }, …
  ],
  "start": <integer: start of time range as ISO 8601 UTC datetime>,
  "end": <integer: end of time range as ISO 8601 UTC datetime>,
}

Org Dashboard Members

GET /api/v1/users/:user/orgs/:org/dashboards/:dashboard/members

GET /api/v1/users/current/orgs/:org/dashboards/:dashboard/members

Description

List an organization’s members.

URL Parameters

Scope Required

read_orgs

Example Response

Response Code: 200

{
  "data": [
    {
      "id": <string: unique id of user>,
      "email": <string: email address>,
      "full_name": <string: full name of user>,
      "is_view_only": <boolean: when true, this member’s coding activity is hidden from the dashboard>,
      "photo": <string: url of photo for this user>,
      "username": <string: users public username>,
    }, …
  ],
  "next_page": <integer: the next page number, if available>,
  "page": <integer: the current page number>,
  "prev_page": <integer: the previous page number, if available>,
  "total": <integer: total number of dashboard members>,
  "total_pages": <integer: number of pages available>,
}

Org Dashboards

GET /api/v1/users/:user/orgs/:org/dashboards

GET /api/v1/users/current/orgs/:org/dashboards

Description

List the organization’s dashboards.

URL Parameters

Scope Required

read_orgs

Example Response

Response Code: 200

{
  "data": [
    {
      "id": <string: unique id of this dashboard>,
      "full_name": <string: this dashboard’s name>,
      "created_by": <string: name of user who created this dashboard>,
      "timezone": <string: the dashboard's timezone in Olson Country/Region format; defaults to the organization’s timezone>,
      "has_changed_timezone": <boolean: whether this dashboard’s timezone is different from the organization’s timezone preference>,
      "members_count": <integer: total number of members in this dashboard>,
      "members_count_human_readable": <string: number of members in this dashboard as string>,
      "is_current_user_member": <boolean: whether the currently authenticated user is a member of this dashboard>,
      "can_current_user_view": <boolean: whether the currently authenticated user can view this dashboard>,
      "can_current_user_request_to_view": <boolean: whether the currently authenticated user can request to view this dashboard>,
      "can_current_user_request_to_join": <boolean: whether the currently authenticated user can request to join this dashboard>,
      "can_current_user_add_members": <boolean: whether the currently authenticated user can add members to this dashboard>,
      "can_current_user_remove_members": <boolean: whether the currently authenticated user can remove members from this dashboard>,
      "can_current_user_delete": <boolean: whether the currently authenticated user can delete this dashboard>,
      "created_at": <datetime: time when user was created in ISO 8601 format>,
      "modified_at": <datetime: time when user was last modified in ISO 8601 format>,
    }, …
  ],
  "next_page": <integer: the next page number, if available>,
  "page": <integer: the current page number>,
  "prev_page": <integer: the previous page number, if available>,
  "total": <integer: total number of dashboards in this org>,
  "total_pages": <integer: number of pages available>,
}

Orgs

GET /api/v1/users/:user/orgs

GET /api/v1/users/current/orgs

Description

List a user’s organizations.

URL Parameters

Scope Required

read_orgs

Example Response

Response Code: 200

{
  "data": [
    {
      "id": <string: unique id of org>,
      "name": <string: the org’s name.>,
      "default_project_privacy": <string: the user’s default privacy for projects on dashboards; can be "visible" or "hidden">,
      "invited_people_count": <integer: number of pending invites>,
      "invited_people_count_human_readable": <string: number of pending invites as string>,
      "is_duration_visible": <boolean: when true, people in this org can see each other’s durations coding activity>,
      "people_count": <integer: number of people in this org>,
      "people_count_human_readable": <string: number of people in this org as string>,
      "timeout": <integer: this organization’s timeout preference>,
      "timezone": <integer: this organization’s timezone preference>,
      "writes_only": <integer: this organization’s writes-only preference>
      "can_current_user_list_dashboards": <boolean: whether the currently authenticated user can list dashboards>,
      "can_current_user_create_dashboards": <boolean: whether the currently authenticated user can create dashboards>,
      "can_current_user_display_coding_on_dashboards": <boolean: whether the currently authenticated user can display their coding activity on dashboards>,
      "can_current_user_view_all_dashboards": <boolean: whether the currently authenticated user can view dashboards in this org without first being invited>,
      "can_current_user_add_people_to_dashboards": <boolean: whether the currently authenticated user can add people to dashboards>,
      "can_current_user_remove_people_from_dashboards": <boolean: whether the currently authenticated user can remove people from dashboards>,
      "can_current_user_edit_and_delete_dashboards": <boolean: whether the currently authenticated user can edit and delete dashboards>,
      "can_current_user_add_people_to_org": <boolean: whether the currently authenticated user can add people to this org>,
      "can_current_user_remove_people_from_org": <boolean: whether the currently authenticated user can remove people from this org>,
      "can_current_user_manage_groups": <boolean: whether the currently authenticated user can add, manage, and delete groups and permissions>,
      "can_current_user_view_audit_log": <boolean: whether the currently authenticated user can view the org’s audit log>,
      "can_current_user_edit_org": <boolean: whether the currently authenticated user can edit this org’s preferences>,
      "can_current_user_manage_billing": <boolean: whether the currently authenticated user can manage this org’s billing>,
      "can_current_user_delete_org": <boolean: whether the currently authenticated user can delete this org>,
      "created_at": <datetime: time when user was created in ISO 8601 format>,
      "modified_at": <datetime: time when user was last modified in ISO 8601 format>,
    }, …
  ],
  "next_page": <integer: the next page number, if available>,
  "page": <integer: the current page number>,
  "prev_page": <integer: the previous page number, if available>,
  "total": <integer: total number of orgs>,
  "total_pages": <integer: number of pages available>,
}

Private Leaderboards

GET /api/v1/users/:user/leaderboards

GET /api/v1/users/current/leaderboards

Description

List user’s private leaderboards. Same as this page.

URL Parameters

Scope Required

read_private_leaderboards

Example Response

Response Code: 200

{
  "data": [
    {
      "can_delete": <boolean: true if user has access to delete this leaderboard>,
      "can_edit": <boolean: true if user has access to edit this leaderboard>,
      "created_at": <datetime: time when leaderboard was created in ISO 8601 format>,
      "has_available_seat": <boolean: true if this leaderboard has room for more members>,
      "id": <string: unique id of leaderboard>,
      "members_count": <int: number of members in this private leaderboard>,
      "members_with_timezones_count": <int: number of members who have timezones set; when a user does not have a timezone, they will be hidden from leaderboards>,
      "modified_at": <datetime: time when leaderboard was last modified in ISO 8601 format>,
      "name": <string: display name>,
      "time_range": <string: time range of this leaderboard; always "last_7_days">,
    }, …
  ],
  "total": <integer: total number of private leaderboards>,
  "total_pages": <integer: number of pages available>,
}

Try it out

Private Leaderboards Leaders

GET /api/v1/users/:user/leaderboards/:board

GET /api/v1/users/current/leaderboards/:board

Description

List of users in this private leaderboard ranked by coding activity in descending order.

URL Parameters

language - String - optional - Filter leaders by a specific language.

page - Integer - optional - Page number of leaderboard.

Scope Required

read_private_leaderboards

Example Response

Response Code: 200

{
  "data": [
    {
      "rank": <int: rank of this leaderboard member>,
      "running_total": {
        "total_seconds": <float: total coding activity for this user as seconds>,
        "human_readable_total": <string: total coding activity for this user as human readable string>,
        "daily_average": <float: daily average for this user as seconds>,
        "human_readable_daily_average": <string: daily average for this user as human readable string>,
        "languages": [
          {
            "name": <string: language name>,
            "total_seconds": <float: total seconds user has logged in this language>,
          }, …
        ],
      },
      "user": {
        "id": <string: unique id of user>,
        "email": <string: email address of user, if public>,
        "username": <string: users public username>,
        "full_name": <string: full name of user>,
        "display_name": <string: display name of this user taken from full_name or @username. Defaults to 'Anonymous User'>,
        "website": <string: website of user>,
        "human_readable_website": <string: website of user without url scheme>,
        "location": <string: location of user>,
        "email_public": <boolean: whether this user's email should be shown publicly on leader boards>,
        "photo_public": <boolean: whether this user's photo should be shown publicly on leader boards>,
      },
    }, …
  ],
  "language": <integer: total number of private leaderboards>,
  "modified_at": <datetime: time when leaderboard was last modified in ISO 8601 format>,
  "page": <int: current page>,
  "range": {
    "start_date": <integer: start of this range as ISO 8601 UTC datetime>,
    "start_text": <string: start of range in human-readable format relative to the current day>,
    "end_date": <integer: end of range as ISO 8601 UTC datetime>,
    "end_text": <string: end of range in human-readable format relative to the current day>,
    "name": <string: time range of this leaderboard>,
    "text": <string: time range in human-readable format relative to the current day>,
  }
  "timeout": <integer: timeout setting in minutes used by this leaderboard>,
  "total_pages": <integer: number of pages available>,
  "writes_only": <boolean: writes_only setting used by this leaderboard>,
}

Projects

GET /api/v1/users/:user/projects

GET /api/v1/users/current/projects

Description

List of WakaTime projects for the current user.

URL Parameters

Scope Required

read_logged_time

Example Response

Response Code: 200

{
  "data": [
    {
      "id": <string: unique project id>,
      "name": <string: project name>,
      "repository": <string: associated repository if connected>,
    }, …
  ],
}

Stats

GET /api/v1/users/:user/stats/:range

GET /api/v1/users/current/stats/:range

Description

A user's coding activity for the given time range. range can be one of last_7_days, last_30_days, last_6_months, or last_year.

URL Parameters

timeout - Integer - optional - The timeout value used to calculate these stats. Defaults the the user's timeout value.

writes_only - Boolean - optional - The writes_only value used to calculate these stats. Defaults to the user's writes_only setting.

project - String - optional - Show more detailed stats limited to this project.

Scope Required

read_stats

Example Response

Response Code: 200

{
  "data": {
    "total_seconds": <float: total coding activity as seconds for the given range of time>,
    "human_readable_total": <string: total coding activity as human readable string>,
    "daily_average": <float: average coding activity per day as seconds for the given range of time>,
    "human_readable_daily_average": <string: daily average as human readable string>,
    "projects": [
      {
        "name": <string: project name>,
        "total_seconds": <float: total coding activity as seconds>,
        "percent": <float: percent of time spent in this project>,
        "digital": <string: total coding activity for this project in digital clock format>,
        "text": <string: total coding activity in human readable format>,
        "hours": <integer: hours portion of coding activity for this project>,
        "minutes": <integer: minutes portion of coding activity for this project>
      }, …
    ],
    "languages": [
      {
        "name": <string: language name>,
        "total_seconds": <float: total coding activity spent in this language as seconds>,
        "percent": <float: percent of time spent in this language>,
        "digital": <string: total coding activity for this language in digital clock format>,
        "text": <string: total coding activity in human readable format>,
        "hours": <integer: hours portion of coding activity for this language>,
        "minutes": <integer: minutes portion of coding activity for this language>,
        "seconds": <integer: seconds portion of coding activity for this language>
      }, …
    ],
    "editors": [
      {
        "name": <string: editor name>,
        "total_seconds": <float: total coding activity spent in this editor as seconds>,
        "percent": <float: percent of time spent in this editor>,
        "digital": <string: total coding activity for this editor in digital clock format>,
        "text": <string: total coding activity in human readable format>,
        "hours": <integer: hours portion of coding activity for this editor>,
        "minutes": <integer: minutes portion of coding activity for this editor>,
        "seconds": <integer: seconds portion of coding activity for this editor>
      }, …
    ],
    "operating_systems": [
      {
        "name": <string: os name>,
        "total_seconds": <float: total coding activity spent in this os as seconds>,
        "percent": <float: percent of time spent in this os>,
        "digital": <string: total coding activity for this os in digital clock format>,
        "text": <string: total coding activity in human readable format>,
        "hours": <integer: hours portion of coding activity for this os>,
        "minutes": <integer: minutes portion of coding activity for this os>,
        "seconds": <integer: seconds portion of coding activity for this os>
      }, …
    ],
    "dependencies": [
      {
        "name": <string: dependency name>,
        "total_seconds": <float: total coding activity spent in this dependency as seconds>,
        "percent": <float: percent of time spent in this dependency>,
        "digital": <string: total coding activity for this dependency in digital clock format>,
        "text": <string: total coding activity in human readable format>,
        "hours": <integer: hours portion of coding activity for this dependency>,
        "minutes": <integer: minutes portion of coding activity for this dependency>,
        "seconds": <integer: seconds portion of coding activity for this dependency>
      }, …
    ],
    "machines": [
      {
        "name": <string: machine hostname and ip address>,
        "machine_name_id": <string: unique id of this machine>,
        "total_seconds": <float: total coding activity spent on this machine as seconds>,
        "percent": <float: percent of time spent on this machine>,
        "digital": <string: total coding activity for this machine in digital clock format>,
        "text": <string: total coding activity in human readable format>,
        "hours": <integer: hours portion of coding activity for this machine>,
        "minutes": <integer: minutes portion of coding activity for this machine>,
        "seconds": <integer: seconds portion of coding activity for this machine>
      }, …
    ],
    "best_day": {
      "date": <string: day with most coding time logged as Date string in YEAR-MONTH-DAY format>,
      "text": <string: total coding activity for this day in human readable format>,
      "total_seconds": <float: number of seconds of coding activity for this day>
    },
    "range": <string: time range of these stats>,
    "holidays": <integer: number of days in this range with no coding time logged>,
    "days_including_holidays": <integer: number of days in this range>,
    "days_minus_holidays": <integer: number of days in this range excluding days with no coding time logged>,
    "status": <string: status of these stats in the cache>,
    "is_already_updating": <boolean: true if these stats are being updated in the background>,
    "is_coding_activity_visible": <boolean: true if this user's coding activity is publicly visible>,
    "is_other_usage_visible": <boolean: true if this user's languages, editors, and operating system stats are publicly visible>,
    "is_stuck": <boolean: true if these stats got stuck while processing and will be recalculated in the background>,
    "is_up_to_date": <boolean: true if these stats are up to date>,
    "start": <integer: start of this time range as ISO 8601 UTC datetime>,
    "end": <integer: end of this time range as ISO 8601 UTC datetime>,
    "timezone": <string: timezone used in Olson Country/Region format>,
    "timeout": <integer: value of the user's timeout setting in minutes>,
    "writes_only": <boolean: status of the user's writes_only setting>,
    "user_id": <string: unique id of this user>,
    "username": <string: public username for this user>,
    "created_at": <datetime: time when these stats were created in ISO 8601 format>,
    "modified_at": <datetime: time when these stats were last updated in ISO 8601 format>
  }
}

Summaries

GET /api/v1/users/:user/summaries

GET /api/v1/users/current/summaries

Description

A user's coding activity for the given time range as an array of summaries segmented by day.

URL Parameters

start - Date - required - Start date of the time range.

end - Date - required - End date of the time range.

project - String - optional - Only show time logged to this project.

branches - String - optional - Only show coding activity for these branches; comma separated list of branch names.

Scope Required

read_logged_time

Example Response

Response Code: 200

{
  "data": [
    {
      "grand_total": {
        "digital": <string: total coding activity in digital clock format>,
        "hours": <integer: hours portion of coding activity>,
        "minutes": <integer: minutes portion of coding activity>,
        "text": <string: total coding activity in human readable format>,
        "total_seconds": <float: total coding activity as seconds>
      },
      "projects": [
        {
          "name": <string: project name>,
          "total_seconds": <float: total coding activity as seconds>,
          "percent": <float: percent of time spent in this project>,
          "digital": <string: total coding activity for this project in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this project>,
          "minutes": <integer: minutes portion of coding activity for this project>
        }, …
      ],
      "languages": [
        {
          "name": <string: language name>,
          "total_seconds": <float: total coding activity spent in this language as seconds>,
          "percent": <float: percent of time spent in this language>,
          "digital": <string: total coding activity for this language in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this language>,
          "minutes": <integer: minutes portion of coding activity for this language>,
          "seconds": <integer: seconds portion of coding activity for this language>
        }, …
      ],
      "editors": [
        {
          "name": <string: editor name>,
          "total_seconds": <float: total coding activity spent in this editor as seconds>,
          "percent": <float: percent of time spent in this editor>,
          "digital": <string: total coding activity for this editor in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this editor>,
          "minutes": <integer: minutes portion of coding activity for this editor>,
          "seconds": <integer: seconds portion of coding activity for this editor>
        }, …
      ],
      "operating_systems": [
        {
          "name": <string: os name>,
          "total_seconds": <float: total coding activity spent in this os as seconds>,
          "percent": <float: percent of time spent in this os>,
          "digital": <string: total coding activity for this os in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this os>,
          "minutes": <integer: minutes portion of coding activity for this os>,
          "seconds": <integer: seconds portion of coding activity for this os>
        }, …
      ],
      "dependencies": [
        {
          "name": <string: dependency name>,
          "total_seconds": <float: total coding activity spent in this dependency as seconds>,
          "percent": <float: percent of time spent in this dependency>,
          "digital": <string: total coding activity for this dependency in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this dependency>,
          "minutes": <integer: minutes portion of coding activity for this dependency>,
          "seconds": <integer: seconds portion of coding activity for this dependency>
        }, …
      ],
      "machines": [
        {
          "name": <string: machine hostname and ip address>,
          "machine_name_id": <string: unique id of this machine>,
          "total_seconds": <float: total coding activity spent on this machine as seconds>,
          "percent": <float: percent of time spent on this machine>,
          "digital": <string: total coding activity for this machine in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this machine>,
          "minutes": <integer: minutes portion of coding activity for this machine>,
          "seconds": <integer: seconds portion of coding activity for this machine>
        }, …
      ],
      "branches": [ // included only when project url parameter used
        {
          "name": <string: branch name>,
          "total_seconds": <float: total coding activity spent in this branch as seconds>,
          "percent": <float: percent of time spent in this branch>,
          "digital": <string: total coding activity for this branch in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this branch>,
          "minutes": <integer: minutes portion of coding activity for this branch>,
          "seconds": <integer: seconds portion of coding activity for this branch>
        }, …
      ],
      "entities": [ // included only when project url parameter used
        {
          "name": <string: entity name>,
          "total_seconds": <float: total coding activity spent in this entity as seconds>,
          "percent": <float: percent of time spent in this entity>,
          "digital": <string: total coding activity for this entity in digital clock format>,
          "text": <string: total coding activity in human readable format>,
          "hours": <integer: hours portion of coding activity for this entity>,
          "minutes": <integer: minutes portion of coding activity for this entity>,
          "seconds": <integer: seconds portion of coding activity for this entity>
        }, …
      ],
      "range": {
        "date": <string: this day as Date string in YEAR-MONTH-DAY format>,
        "start": <integer: start of this day as ISO 8601 UTC datetime>,
        "end": <integer: end of this day as ISO 8601 UTC datetime>,
        "text": <string: this day in human-readable format relative to the current day>,
        "timezone": <string: timezone used in Olson Country/Region format>
      }
    }, …
  ],
  "start": <integer: start of time range as ISO 8601 UTC datetime>,
  "end": <integer: end of time range as ISO 8601 UTC datetime>,
}

User Agents

GET /api/v1/users/:user/user_agents

GET /api/v1/users/current/user_agents

Description

List of plugins which have sent data for this user.

URL Parameters

Scope Required

read_logged_time

Example Response

Response Code: 200

{
  "data": {
    "id": <string: unique id of this user agent>,
    "value": <string: a user agent string>,
    "editor": <string: the editor/IDE name of this user agent>,
    "version": <string: the wakatime plugin version of this user agent>,
    "os": <string: operating system of this user agent>,
    "last_seen": <datetime: time when this user agent was last seen in ISO 8601 format>,
    "created_at": <datetime: time when this user agent was first seen in ISO 8601 format>,
  },
}

Users

GET /api/v1/users/:user

GET /api/v1/users/current

Description

A single user.

URL Parameters

Scope Required

email

Example Response

Response Code: 200

{
  "data": {
    "id": <string: unique id of user>,
    "has_premium_features": <boolean: true if user has access to premium features>,
    "display_name": <string: display name of this user taken from full_name or @username. Defaults to 'Anonymous User'>,
    "full_name": <string: full name of user>,
    "email": <string: email address>,
    "photo": <string: url of photo for this user>,
    "email_public": <boolean: whether this user's email should be shown on the public leader board>,
    "is_email_confirmed": <boolean: whether this user's email address has been verified with a confirmation email>,
    "photo_public": <boolean: whether this user's photo should be shown on the public leader board>,
    "timezone": <string: user's timezone in Olson Country/Region format>,
    "last_heartbeat_at": <datetime: time of most recent heartbeat received>,
    "last_plugin": <string: user-agent string from the last plugin used>,
    "last_plugin_name": <string: name of editor last used>,
    "last_project": <string: name of last project coded in>,
    "plan": <string: users subscription plan>,
    "username": <string: users public username>,
    "website": <string: website of user>,
    "human_readable_website": <string: website of user without protocol part>,
    "location": <string: location of user>,
    "logged_time_public": <boolean: coding activity should be shown on the public leader board>,
    "languages_used_public": <boolean: languages used should be shown on the public leader board>,
    "is_hireable": <boolean: user preference, not currently used>,
    "created_at": <datetime: time when user was created in ISO 8601 format>,
    "modified_at": <datetime: time when user was last modified in ISO 8601 format>,
  },
}