NAV Navbar
shell javascript

Summary

The Smart Citizen API is a publicly available interface allowing anyone to develop applications on top of the Smart Citizen platform. For more general and hardware information check the documentation.

# Shell example
# In the shell examples we use either `curl` or the `http`
// Javascript example
# The json responses will look something like this:
[
  {
    "example_response":"example_value"
  }
]

Schema

In a general sense, any user can own as many device as needed. Each device represents a "real" device, containing sensors, which perform measurements. A device in a real world can be registered multiple times in the API, but it will only store data in one device. In addition, user can create experiments, which are collection of devices with a certain purpose. This feature is currently experimental!

SmartCitizen UML

All API access is over HTTPS and accessed via api.smartcitizen.me. Some overall characteristics to bear in mind:

Root Endpoint

You can issue a GET request to the root endpoint to get all the endpoint categories that the API supports. From all the possible endpoints, you will mostly care about devices, measurements, sensors and users.

$ curl https://api.smartcitizen.me

http GET https://api.smartcitizen.me/v0/
// Run this in your browser console
fetch('https://api.smartcitizen.me/v0/')
  .then(function(response) {
    return response.json();
  })
  .then(function(myJson) {
    console.log(JSON.stringify(myJson));
  });
HTTP/1.1 200 OK
{
    "notice":"Welcome. The old API has been removed.",
    "api_documentation_url":"https://developer.smartcitizen.me",
    "current_user_url":"https://api.smartcitizen.me/v0/me",
    "devices_url":"https://api.smartcitizen.me/v0/devices",
    "measurements_url":"https://api.smartcitizen.me/v0/measurements",
    "sensors_url":"https://api.smartcitizen.me/v0/sensors",
    "users_url":"https://api.smartcitizen.me/v0/users",
    "tags_url":"https://api.smartcitizen.me/v0/tags",
    "tags_sensors_url":"https://api.smartcitizen.me/v0/tag_sensors",
    "version_git":"1.1.5\n"
}

Versioning

By default and, for now, all requests receive the v0 version of the API. We encourage you to explicitly request this version via the URL or the HTTP Accept header.

endpoint
BAD https://api.smartcitizen.me/users
GOOD https://api.smartcitizen.me/v0/users

Accept: application/vnd.smartcitizen; version=0,application/json

Authentication

There are 2 ways you can access the API. OAuth 2.0 is the recommended method.

OAuth 2.0

# Send authenticated POST for username 'user1', which should return the 'access_token'
$ curl -XPOST https://api.smartcitizen.me/v0/sessions -d "username=user1" -d "password=password"

# OAuth2 Token (sent as a parameter)
$ curl -G https://api.smartcitizen.me/v0/me?access_token=OAUTH-TOKEN

# OAuth2 Token (sent in a header)
$ curl -H "Authorization: Bearer OAUTH-TOKEN" https://api.smartcitizen.me/v0/me

You can obtain a general access_key by sending an authenticated POST request to https://api.smartcitizen.me/v0/sessions

A basic example resides here https://example.smartcitizen.me and its source code is here https://github.com/johnrees/smartcitizen-oauth-example.

HTTP Basic Auth

# Add a base64 encoded hash of 'username:password' in the header
curl 'https://api.smartcitizen.me/v0/me' -H 'Authorization: Basic am9objpzbWFydHBhc3M='

# NOT RECOMMENDED - add username and password in the header
curl 'https://api.smartcitizen.me/v0/me' --user username:password

Filtering Responses

Pagination

$ curl --include 'https://api.smartcitizen.me/v0/users?page=5'
HTTP/1.1 200 OK
Link: <https://api.smartcitizen.me/v0/users?page=1>; rel="first",
  <https://api.smartcitizen.me/v0/users?page=173>; rel="last",
  <https://api.smartcitizen.me/v0/users?page=6>; rel="next",
  <https://api.smartcitizen.me/v0/users?page=4>; rel="prev"
Total: 4321
Per-Page: 25

Most endpoints that return more than a single result e.g. /v0/users, v0/devices will return blocks of the result set that can be manipulated using the following parameters.

Parameter Default Description
page
integer
1 page
per_page
integer
25 page

The headers will include links to the Total results count, number of results shown Per-Page and first, last, next and previous results.

curl -XGET https://api.smartcitizen.me/v0/search?q=barcelona

HTTP/1.1 200 OK
[
{
  "id": 506,
  "type": "Device",
  "name": "Barceloneta Sensor",
  "description": "Barcelona sensor place at a 7th floor in front of the beach. Working on different batteries to have more autonomy outdoors. Next: Solar Panel!",
  "owner_id": 3,
  "owner_username": "tomasdiez",
  "city": "Barcelona",
  "country_code": "ES"
}
...

To search both Users and Devices at the same time you can use the global search endpoint.

Required Parameters

Parameter Description
q
string
Query string

Response

There can be two types of object included in the response array, Devices and Users.

Device Object

Parameter Description
id
integer
Unique ID for the device
name
string
Name of the device
owner_id
integer
Unique ID of the device's owner
owner_username
string
Unique username of the device's owner
city
string
City the device is in
country_code
string
Alpha-2 country code of the device

User Object

Parameter Description
id
integer
Unique ID for the user
username
string
Unique username of the user
avatar
string
URL of the users avatar
city
string
City the user is in
country_code
string
Alpha-2 country code of the user

Basic Searching

Similar to the pagination, you can filter and sort most responses that return more than one result. This is done with the Ransack library. You can query different endpoints and filter them by using search matchers.

https://github.com/activerecord-hackery/ransack/wiki/Basic-Searching

For information about the Search Matchers, check the Ransack documentation.

Keys for devices

Key
id
name
description
owner_username
owner_id
created_at
updated_at
last_recorded_at
state
exposure
kit_id
geohash
uuid

Keys for users

Key
id
username
created_at
updated_at
city
country_code
uuid

Examples

Query Type Value Description
/users?q[username_eq]=adam string adam Users where first name equals 'Adam'
/devices?q[owner_id_eq]=1 integer 1 Devices where owner ID equals 1
/devices?q[tags_name_in]=Barcelona string Barcelona Devices which have the tag 'Barcelona' (case sensitive).
/devices?with_tags=Barcelona|Amsterdam string Barcelona|Amsterdam Devices which have ANY of the tags separated by PIPE |
/devices?q[postprocessing_id_not_null]=1 integer 1 Devices where postprocessing is not_null
/sensors?q[id_lt]=100 integer 100 Sensors where ID less than 100
/users?q[username_cont]=sck string sck Users where username contains 'sck'

Sorting Results

You can order results with the q[sort] parameter

Parameter Value Description
/users?q[sort]=username%20asc
string
username asc Users ordered by username in ASCENDING order
/devices?q[sort]=id%20desc
integer
id desc Devices ordered by id in DESCENDING order

Pretty Printing

# Pretty Response
curl "https://api.smartcitizen.me/v0/sensors/10?pretty=true"

Result:

{
  "id" : 10,
  "name" : "Battery",
  "description" : "Custom Circuit",
  "unit" : "%",
  "created_at" : "2015-02-02T18:18:00.276Z",
  "updated_at" : "2015-02-02T18:18:00.276Z"
}

You can format responses so that they are easier to read by adding pretty=true to a request.

Users

Add a User

POST https://api.smartcitizen.me/v0/users

http POST https://api.smartcitizen.me/v0/users email=testing@test.com password=testpass username=testinguser
HTTP/1.1 201 Created
{
    "avatar": "http://smartcitizen.s3.amazonaws.com/avatars/default.svg",
    "devices": [],
    "email": "[FILTERED]",
    "id": 3858,
    "joined_at": "2015-07-31T10:20:27Z",
    "location": {
        "city": null,
        "country": null,
        "country_code": null
    },
    "role": "citizen",
    "updated_at": "2015-07-31T10:20:27Z",
    "url": null,
    "username": "testinguser",
    "uuid": null
}

Most actions on the API require authenticated access. To obtain an OAuth 2.0 access_token the first step is to have a user account.

Parameter Required? Description
email
string
Email address of the user
username
string
Username of the user
password
string
Password of the user
city
string
City where the user is located
country_code
string
2 letter country-code of the user
url
string
Webpage of the user

Get Current User (me)

GET https://api.smartcitizen.me/v0/me

http GET https://api.smartcitizen.me/v0/me access_token=123456789
HTTP/1.1 200 OK
{
  "avatar": "http://images.smartcitizen.me/s100/feca2180/firewatch-4.jpg",
  "devices": [
    {
      "added_at": "2015-07-31T10:11:09Z",
      "description": "new description",
      "id": 1816,
      "kit_id": null,
      "last_reading_at": null,
      "latitude": null,
      "longitude": null,
      "mac_address": "00:0a:95:9d:68:16",
      "name": "my sck",
      "state": "never_published",
      "system_tags": [
        "new",
        "offline"
      ],
      "updated_at": "2015-07-31T10:15:06Z",
      "uuid": "cb480089-c000-4e69-96c0-ad6378f3a537"
    }
  ],
  "email": "john@bitsushi.com",
  "id": 2997,
  "joined_at": "2015-02-02T15:17:28Z",
  "location": {
    "city": "Barcelona",
    "country": "Spain",
    "country_code": "ES"
  },
  "role": "citizen",
  "updated_at": "2015-07-31T10:12:46Z",
  "url": "http://www.google.com",
  "username": "john",
  "uuid": "feca2180-d0dd-49fd-8815-ec59ca6d48f6"
}

Used to retrieve information about the currently authenticated user. It returns a detailed representation of the user.

Field Description
id*
integer
Autoincrementing unique ID for the user
uuid*
uuid
Unique ID for the user
role*
string
There are currently three different roles: citizen, researcher and admin. See role.
username*
string
Username of the user
profile_picture*
file
Upload the image that represents the user. It will return a Rails active_storage link to the asset
url
string
Webpage of the user
location.city
string
City in which the user is located
location.country
string
Full country name. Automatically generated from country_code, using this data
location.country_code
string
2 letter country-code of the user
updated_at*
datetime
The date and time that the user updated data on the platform
email
string
Email address of the authenticated user, will be [FILTERED] for unauthenticated requests
forwarding_token
string
Hash containing a forwarding secret topic to be used in data forwarding
forwarding_username
string
Hash containing a forwarding secret username to be used in data forwarding
devices
array
Array of devices that the user owns on the platform

Roles

The role defines privileges of the user, for which citizen is the default role. admin accounts have full access to the platform, while researchers can enable data forwarding for the devices they own. This differentiation is done to allow experimental features, such as forwarding, to be tested in a more restricted environments and see how they scale. researcher roles do not have throttling on API requests, while citizen requests are limited to 90 requests/minute. Beyond these two differences, there is no other impact on the data or actions allowed. You can write us to have researcher access at our support mail.

Update Current User

PATCH https://api.smartcitizen.me/v0/me

http PATCH https://api.smartcitizen.me/v0/me access_token=randomToken1234
HTTP/1.1 200 OK
{
  "avatar": "http://images.smartcitizen.me/s100/feca2180/firewatch-4.jpg",
  "devices": [
    {
      "added_at": "2015-07-31T10:11:09Z",
      "description": null,
      "id": 1816,
      "kit_id": null,
      "last_reading_at": null,
      "latitude": null,
      "longitude": null,
      "mac_address": "00:0a:95:9d:68:16",
      "name": "my sck",
      "state": "never_published",
      "system_tags": [
        "new",
        "offline"
      ],
      "updated_at": "2015-07-31T10:11:09Z",
      "uuid": "cb480089-c000-4e69-96c0-ad6378f3a537"
    }
  ],
  "email": "john@bitsushi.com",
  "id": 2997,
  "joined_at": "2015-02-02T15:17:28Z",
  "location": {
    "city": "Barcelona",
    "country": "Spain",
    "country_code": "ES"
  },
  "role": "citizen",
  "updated_at": "2015-07-31T10:12:46Z",
  "url": "http://www.google.com",
  "username": "john",
  "uuid": "feca2180-d0dd-49fd-8815-ec59ca6d48f6"
}

An authenticated user can update their own details. They have the same parameters used as adding a user.

Change an Avatar

This is the only supported way, using Rails Active Storage:

curl -XPATCH 'https://api.smartcitizen.me/v0/me?access_token=MYAPITOKEN' --form "profile_picture=@mypicture.jpeg"

Reset a Password

http POST https://api.smartcitizen.me/v0/password_resets?username=testing
HTTP/1.1 200 OK
{
  "message": "Password Reset Instructions Delivered"
}
# password reset email has been sent to user: testing

Step 1 of 4

Initiate the password reset.

POST https://api.smartcitizen.me/v0/password_resets?email_or_username=username

or

POST https://api.smartcitizen.me/v0/password_resets?email_or_username=email

Step 2 of 4

An email is sent to the user, containing a PASSWORD_RESET_TOKEN.

Step 3 of 4

Return the User(username=USERNAME) object.

POST https://api.smartcitizen.me/v0/password_resets/:password_reset_token

Step 4 of 4

Set the new password.

PATCH https://api.smartcitizen.me/v0/password_resets/:password_reset_token?password=password

Get All Users

GET https://api.smartcitizen.me/v0/users

http GET https://api.smartcitizen.me/v0/users
HTTP/1.1 200 OK
[
{
  "id": 1,
  "uuid": "4725977d-0490-4984-b5a4-df2a483a85ae",
  "role": "admin",
  "username": "testing",
  "avatar": "https://images.smartcitizen.me/s100/avatars/472/1arck5q.firewatch-6.jpg",
  "url": null,
  "location": {
    "city": null,
    "country": null,
    "country_code": null
  },
  "joined_at": "2015-01-27T18:43:26Z",
  "updated_at": "2015-07-30T09:59:28Z",
  "email": "[FILTERED]",
  "devices": [
    {
      "id": 1148,
      "uuid": "dd4b6f66-5b51-44d0-a9de-e7fd1999287d",
      "mac_address": "[FILTERED]",
      "name": null,
      "description": null,
      "latitude": 52.3079989,
      "longitude": 4.97154509999996,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "offline",
        "outdoor"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:49Z",
      "updated_at": "2015-05-25T07:31:28Z"
    },
    {
      "id": 1762,
      "uuid": "f119ff40-348c-4827-b266-06c3a4e5fbe3",
      "mac_address": "[FILTERED]",
      "name": "RyanLim",
      "description": "Tiong Bahru",
      "latitude": 1.28645,
      "longitude": 103.826917,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:51Z",
      "updated_at": "2015-05-25T07:31:29Z"
    },
    {
      "id": 344,
      "uuid": "c6b1792d-8a0d-44f0-bce3-89cb6819dac5",
      "mac_address": "[FILTERED]",
      "name": "SmartCitizenSk",
      "description": null,
      "latitude": 53.406754,
      "longitude": -2.158843,
      "kit_id": 2,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:47Z",
      "updated_at": "2015-05-25T07:31:27Z"
    },
    {
      "id": 1242,
      "uuid": "da84118a-4e49-4c59-baf1-f622a10b69de",
      "mac_address": "[FILTERED]",
      "name": null,
      "description": null,
      "latitude": 52.3079989,
      "longitude": 4.97154509999996,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "offline",
        "outdoor"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:49Z",
      "updated_at": "2015-05-25T07:31:28Z"
    },
    {
      "id": 860,
      "uuid": "937c78eb-ec19-47c0-a9ad-1be6cec4b8d6",
      "mac_address": "[FILTERED]",
      "name": "Bwired.nl",
      "description": null,
      "latitude": 51.7242901136958,
      "longitude": 5.30086557678224,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:48Z",
      "updated_at": "2015-05-25T07:31:27Z"
    },
    {
      "id": 1749,
      "uuid": "bb26425d-30ae-4d9b-a6a6-7b828c8ed1ba",
      "mac_address": "[FILTERED]",
      "name": "Yongin1",
      "description": null,
      "latitude": 37.2410864,
      "longitude": 127.1775537,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:51Z",
      "updated_at": "2015-05-25T07:31:28Z"
    },
    {
      "id": 747,
      "uuid": "42beffb0-76b4-4e75-bbd3-2636c5be90fd",
      "mac_address": "[FILTERED]",
      "name": "AroundMe HQ",
      "description": null,
      "latitude": 45.4319105,
      "longitude": 7.80372020000004,
      "kit_id": 2,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:48Z",
      "updated_at": "2015-05-25T07:31:29Z"
    },
    {
      "id": 1149,
      "uuid": "6849e0dd-8265-45b8-8e74-79af064cb092",
      "mac_address": "[FILTERED]",
      "name": "2e kekerstraat",
      "description": null,
      "latitude": 52.3079989,
      "longitude": 4.97154509999996,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "offline",
        "outdoor"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:49Z",
      "updated_at": "2015-05-25T07:31:29Z"
    },
    {
      "id": 1006,
      "uuid": "cb1d8723-66b0-4cae-95c4-4849e513727b",
      "mac_address": "[FILTERED]",
      "name": "SCARNING",
      "description": null,
      "latitude": 52.6724249,
      "longitude": 0.885390000000029,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "offline",
        "outdoor"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:49Z",
      "updated_at": "2015-05-25T07:31:29Z"
    },
    {
      "id": 1760,
      "uuid": "63a923c2-508e-4ac5-b90c-73b8b45561fd",
      "mac_address": "[FILTERED]",
      "name": null,
      "description": null,
      "latitude": 1.2800945,
      "longitude": 103.8509491,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:51Z",
      "updated_at": "2015-05-25T07:31:29Z"
    },
    {
      "id": 605,
      "uuid": "3a86d052-28b4-4ecc-9293-3c5aa40d6a30",
      "mac_address": "[FILTERED]",
      "name": "MySmartCitizenBoard",
      "description": null,
      "latitude": 42.1969689,
      "longitude": -88.0934108,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:48Z",
      "updated_at": "2015-05-25T07:31:31Z"
    },
    {
      "id": 1473,
      "uuid": "8f7724af-50e8-4967-869c-4ff94e016023",
      "mac_address": "[FILTERED]",
      "name": "Village Green Drive",
      "description": null,
      "latitude": 40.9253764,
      "longitude": -73.0473284,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "offline",
        "outdoor"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:50Z",
      "updated_at": "2015-05-25T07:31:31Z"
    },
    {
      "id": 1147,
      "uuid": "e211ea4c-580a-410d-9308-a328aae4d98b",
      "mac_address": "[FILTERED]",
      "name": "Guli's Sensors",
      "description": "This is the ultimate SCK",
      "latitude": 46.8037168264815,
      "longitude": -71.2302180070495,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:49Z",
      "updated_at": "2015-05-25T07:31:31Z"
    },
    {
      "id": 1376,
      "uuid": "0ac3d295-670f-4661-a165-1483ff95bde4",
      "mac_address": "[FILTERED]",
      "name": "KitTest",
      "description": null,
      "latitude": 45.6669011,
      "longitude": 12.243039,
      "kit_id": 3,
      "state": "has_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": "2015-04-27T15:30:20Z",
      "added_at": "2015-02-02T15:59:50Z",
      "updated_at": "2015-05-25T08:43:14Z"
    }
  ]
}
...

This endpoint retrieves all users. This returns the same fields as the me endpoint if authenticated and authorized. Private fields are returned as [FILTERED].

Get a User

GET https://api.smartcitizen.me/v0/users/(:id|:username)

http https://api.smartcitizen.me/v0/users/2
HTTP/1.1 200 OK
{
  "id": 2,
  "uuid": "fdbc41c4-ba01-4bfc-b850-edda889bff2e",
  "role": "citizen",
  "username": "alex",
  "avatar": "http://smartcitizen.s3.amazonaws.com/avatars/default.svg",
  "url": null,
  "location": {
    "city": null,
    "country": null,
    "country_code": null
  },
  "joined_at": "2015-02-02T15:54:37Z",
  "updated_at": "2015-07-21T12:20:54Z",
  "email": "[FILTERED]",
  "devices": [
    {
      "id": 1357,
      "uuid": "791e06b0-d068-4f62-8701-4e41cf15e38a",
      "mac_address": "[FILTERED]",
      "name": "Citizen Science Kit #1",
      "description": "Test Kit for the Innovation Lab Kosovo, within the event Science for change / Citizen Science.",
      "latitude": 42.5813722,
      "longitude": 20.88935,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:50Z",
      "updated_at": "2015-05-25T07:31:28Z"
    },
    {
      "id": 1360,
      "uuid": "206296e5-7837-4587-af91-5b782db42135",
      "mac_address": "[FILTERED]",
      "name": "Citizen Science Pristina #2",
      "description": "this kit is to monitor the air quality in the area of Pristina and is part of the science for change initiative",
      "latitude": 42.7145797355173,
      "longitude": 21.1464852426758,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:50Z",
      "updated_at": "2015-05-25T07:31:28Z"
    },
    {
      "id": 339,
      "uuid": "c7201a30-da4b-4dec-8042-3d30da1b3363",
      "mac_address": "[FILTERED]",
      "name": "Roma Maker Faire",
      "description": "SmartCitizen Kit exhibited in the Maker Faire in Rome\r\n00:06:66:21:17:58",
      "latitude": 41.8343,
      "longitude": 12.473442,
      "kit_id": 2,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:47Z",
      "updated_at": "2015-05-25T07:31:28Z"
    },
    {
      "id": 1402,
      "uuid": "ddd06451-b847-4972-965a-96eef438282e",
      "mac_address": "[FILTERED]",
      "name": "test for Fab10",
      "description": "mhdvsajhgdasjhgasdjhg",
      "latitude": 41.3965424157754,
      "longitude": 2.19476096466298,
      "kit_id": 3,
      "state": "never_published",
      "system_tags": [
        "indoor",
        "offline"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:50Z",
      "updated_at": "2015-05-25T07:31:29Z"
    },
    {
      "id": 12,
      "uuid": "21631212-8633-450e-bd44-f36202d864f6",
      "mac_address": "[FILTERED]",
      "name": "Parisien Sensor",
      "description": "Test from Paris waking up",
      "latitude": 48.84676,
      "longitude": 2.41442,
      "kit_id": 2,
      "state": "never_published",
      "system_tags": [
        "offline",
        "outdoor"
      ],
      "last_reading_at": null,
      "added_at": "2015-02-02T15:59:46Z",
      "updated_at": "2015-05-25T07:31:31Z"
    }
  ]
}

This endpoint retrieves a specific user. If authenticated, it will return the same fields as the me endpoint if authenticated and authorized. Private fields are returned as [FILTERED].

URL Parameters

Parameter Description
ID or username The ID (int) or username (string) of the user to retrieve.

Devices

Get a Device

GET https://api.smartcitizen.me/v0/devices/:id

http GET https://api.smartcitizen.me/v0/devices/1616
HTTP/1.1 200 OK
{
  "id": 1616,
  "uuid": "85543ca2-e543-4351-9122-98756d50e6b1",
  "name": "Orchid Surf Stay Bali",
  "description": "Located at the pool area of the hotel ",
  "state": "has_published",
  "system_tags": [
    "offline",
    "outdoor"
  ],
  "last_reading_at": "2015-07-16T08:53:16Z",
  "added_at": "2015-02-02T15:59:51Z",
  "updated_at": "2015-07-16T08:53:32Z",
  "mac_address": "[FILTERED]",
  "owner": {
    "id": 2247,
    "uuid": "bcd5b918-d89f-4cb6-a2bb-30245904bc2f",
    "username": "JesusZabala",
    "avatar": "http://smartcitizen.s3.amazonaws.com/avatars/default.svg",
    "url": null,
    "joined_at": "2015-02-02T15:55:41Z",
    "location": {
      "city": null,
      "country": null,
      "country_code": null
    },
    "device_ids": [
      1616
    ]
  },
  "data": {
    "recorded_at": "2015-07-16T08:53:32Z",
    "added_at": "2015-07-16T08:53:32Z",
    "firmware": "[IGNORE]",
    "location": {
      "ip": null,
      "exposure": "outdoor",
      "elevation": 1,
      "latitude": -8.82111778712582,
      "longitude": 115.15258114151,
      "geohash": "qw3vu65t38",
      "city": "Kuta Selatan",
      "country_code": "ID",
      "country": "Indonesia"
    },
    "sensors": [
      {
        "id": 10,
        "ancestry": null,
        "name": "Battery",
        "description": "Custom Circuit",
        "unit": "%",
        "created_at": "2015-02-02T18:18:00Z",
        "updated_at": "2015-07-05T19:53:51Z",
        "measurement_id": 7,
        "uuid": "c9ff2784-53a7-4a84-b0fc-90ecc7e313f9",
        "value": 100.0,
        "raw_value": 1000,
        "prev_value": 100.0,
        "prev_raw_value": 1000
      },
      {
        "id": 5,
        "ancestry": "3",
        "name": "DHT22 - Humidity",
        "description": "Humidity",
        "unit": "%",
        "created_at": "2015-02-02T18:15:34Z",
        "updated_at": "2015-07-05T19:53:22Z",
        "measurement_id": 2,
        "uuid": "6b4b64d9-3841-446c-a7f5-63f480932b96",
        "value": 1.0,
        "raw_value": 10,
        "prev_value": 1.0,
        "prev_raw_value": 10
      },
      {
        "id": 4,
        "ancestry": "3",
        "name": "DHT22 - Temperature",
        "description": "Temperature",
        "unit": "ºC",
        "created_at": "2015-02-02T18:15:14Z",
        "updated_at": "2015-07-05T19:53:02Z",
        "measurement_id": 1,
        "uuid": "a50dbd88-b0c7-4094-ad74-2b755e8023a8",
        "value": 29.8,
        "raw_value": 298,
        "prev_value": 29.9,
        "prev_raw_value": 299
      },
      {
        "id": 8,
        "ancestry": null,
        "name": "MICS-2710",
        "description": "MOS NO2 gas sensor",
        "unit": "kOhm (ppm)",
        "created_at": "2015-02-02T18:17:23Z",
        "updated_at": "2015-07-05T19:56:21Z",
        "measurement_id": 6,
        "uuid": "1eb0249d-29d8-41be-8e24-d3b1e5773c0f",
        "value": 197.574,
        "raw_value": 197574,
        "prev_value": 182.971,
        "prev_raw_value": 182971
      },
      {
        "id": 9,
        "ancestry": null,
        "name": "MICS-5525",
        "description": "MOS CO gas sensor",
        "unit": "kOhm (ppm)",
        "created_at": "2015-02-02T18:17:44Z",
        "updated_at": "2015-07-05T19:56:07Z",
        "measurement_id": 5,
        "uuid": "7baaecb7-2586-4063-9c15-bfa999e329aa",
        "value": 276.753,
        "raw_value": 276753,
        "prev_value": 278.468,
        "prev_raw_value": 278468
      },
      {
        "id": 21,
        "ancestry": null,
        "name": "Microchip RN-131",
        "description": "802.11 b/g WiFi",
        "unit": "# networks",
        "created_at": "2015-05-04T11:17:18Z",
        "updated_at": "2015-07-05T19:57:22Z",
        "measurement_id": 9,
        "uuid": "5b1f0e38-336a-4abf-9989-69b48f0026ef",
        "value": 4,
        "raw_value": null,
        "prev_value": 4,
        "prev_raw_value": null
      },
      {
        "id": 7,
        "ancestry": null,
        "name": "POM-3044P-R",
        "description": "Electret microphone with envelope follower sound pressure sensor (noise)",
        "unit": "dB",
        "created_at": "2015-02-02T18:16:41Z",
        "updated_at": "2015-07-05T19:56:59Z",
        "measurement_id": 4,
        "uuid": "5efd2376-6783-476b-bf85-57ead5f89654",
        "value": 67.2,
        "raw_value": 31,
        "prev_value": 59.8,
        "prev_raw_value": 13
      },
      {
        "id": 6,
        "ancestry": null,
        "name": "PVD-P8001",
        "description": "LDR Analog Light Sensor",
        "unit": "%",
        "created_at": "2015-02-02T18:15:55Z",
        "updated_at": "2015-07-05T19:56:43Z",
        "measurement_id": 3,
        "uuid": "0e9cdc5b-d369-4480-9676-bf31af6a5977",
        "value": 1.5,
        "raw_value": 15,
        "prev_value": 1.7,
        "prev_raw_value": 17
      },
      {
        "id": 11,
        "ancestry": null,
        "name": "Solar Panel",
        "description": "Custom Circuit",
        "unit": "mV",
        "created_at": "2015-02-02T18:18:12Z",
        "updated_at": "2015-07-05T19:54:09Z",
        "measurement_id": 8,
        "uuid": "4ab402c5-9297-407a-b0b2-7089520f7ed0",
        "value": 5.066,
        "raw_value": 5066,
        "prev_value": 5.067,
        "prev_raw_value": 5067
      }
    ]
  },
  "kit": {
    "id": 2,
    "uuid": "1409dba9-b06b-4ea5-904c-e0df6e09b903",
    "slug": "sck:1,0",
    "name": "SCK 1.0 - Ambient Board",
    "description": "Goteo Board",
    "created_at": "2015-02-02T18:18:50Z",
    "updated_at": "2015-05-25T14:06:25Z"
  }
}

Returns a single device. Example of a complete response - http://api.smartcitizen.me/v0/devices/1616

Field Example Description
id*
integer
1619 Incremental, unique ID of the device
uuid*
uuid
"fc9d12cf-b3aa-4030-9abf-2315e8f8a65d" Unique ID for the device
name
string
My amazing sensor Name of the device
description
string
An SCK in Southwark Description of the device
state
string
"has_published" (Automatic) state of the device. See state.
system_tags
string array
['new', 'indoor'] See system_tag values table below.
user_tags
string array
['new', 'indoor'] An Array of user tags, predefined from a specific list available in tags.
last_reading_at*
datetime
"2015-04-30T17:56:04.432Z" Last reading from any of the sensors of the device.
created_at*
datetime
"2015-04-30T17:56:04.432Z" When the device was created in the platform.
updated_at*
datetime
"2015-04-30T17:56:04.432Z" When the device info was last updated (it does not get modified by new data).
notify.stopped_publishing
bool
true Notification setting in case the device stopped publishing
notify.low_battery
bool
false Notification setting in case the device has low battery
device_token
string
123abc Device token (secret)
postprocessing
postprocessing
- See data postprocessing
location
location
See location Object containing device's location
data_policy
policy
See data policy Object containing device's data policy
hardware
hardware
See hardware Object containing device's hardware information
owner*
owner
See owner Device's owner information
data
data
See data Data object containing the device's sensors and latest readings

Location

This object contains information on the device location. Lat/long precision is set to 5 digits (equivalent to a resolution of meters). An optional location blurring feature can be enabled with the precise_location feature in the data policy field, for those cases that seek to preserve their location privacy (although the device owner place the pin at a different location at their own will). If precise_location is not enabled, the lat/long precision will still be 5 digits, but the location will be blurred keeping only up to 3 digits of accuracy (hundred meters).

Field Example Description
location.ip
decimal
location.exposure
string
"indoor" Indoor or Outdoor
location.elevation
decimal
25 Elevation of the location where the device is placed
location.longitude
decimal
-0.08622 Longitude of the location where the device is placed
location.latitude
decimal
50.43231 Latitude of the location where the device is placed
location.city
string
Southwark City where the device is located
location.country_code
string
GB Alpha-2 Country Code where the device is located
location.country
string
Great Britain Country where the device is located

Data postprocessing

This information is used to process data on those devices that require some automated data processing tools. Check the docs for more information.

Data Policy

This is used to define the user's priority on their device.

Field Example Description
data_policy.is_private
bool
false If the device is private or not. This hides the device to other users
data_policy.enable_forwarding
bool
false If the device has data forwarding enabled. Currently only available to researchers (see users)
*data_policy.precise_location *
bool
false If the device has a precise location enabled. The user can't store a precise location if this is disabled. See location

Hardware

This object represents the device hardware information.

Field Example Description
hardware.name
string
"SCK 2.1 with CO2" Complete name of the device, including hardware definition and version
hardware.type
string
"SCK" If the hardware is a SCK or other type
hardware.version
string
"2.1" Hardware version, ideally in a major.minor format
hardware.slug
string
"sck,2.1" For internal use only
hardware.last_status_message
status
See status Status message by the device

Status

This message is delivered by Smart Citizen devices via MQTT through the info topic. This is used to retrieve firmware information, and potential debugging information. This is filtered for unauthorised requests.

Field Example Description
id
string
AFF32AD50515157382E3120FF152B26 Serial Number of the main microcontroller
mac
string
86:0D:8E:A7:4E:7D MAC address of the Wi-Fi Antenna
time
datetime
2024-10-03T03:00:18Z When the last status message was received
esp_bd
datetime
2024-10-03T03:00:18Z When the Wi-Fi antenna firmware was built
hw_ver
string
2.1 Hardware version
rcause
string
SYST Reason for last reset of the device
sam_bd
datetime
2024-10-03T03:00:18Z When the main microcontroller firmware was built
esp_ver
string
0.9.8-48c75ee-master Wi-Fi antenna firmware version
sam_ver
string
0.9.8-48c75ee-master Main microcontroller firmware version

State

Represents the device state, defined in an automated way by the platform.

Field Description
not_configured Device has been added to the platform but we do not have its MAC address
never_published Device has been added, we have the MAC but no readings have been received
has_published At least one reading has been recorded, submitted and saved to the platform
archived The device has been temporarily removed from the platform

System Tags

String Description
new The device was added to the platform less than 7 days ago
indoor The device is placed indoors
outdoor The device is placed outdoors (default)

Data

This object contains the latest readings for the device.

Field Example Description
sensors
array of sensors
[sensor] An array of sensor objects, with the latest reading value, prev_value, and date of the reading injected into them. It also includes measurement associated with each.

Add a Device

POST https://api.smartcitizen.me/v0/devices

http POST https://api.smartcitizen.me/v0/devices access_token=9d00b4c027f757ef1c7b254b9f795d1ebd1e04f7a21b01d5a9dfe5f6e37439b5 mac_address='00:0a:95:9d:68:16' name='my sck'
HTTP/1.1 201 Created
{
  "added_at": "2015-07-31T10:11:09Z",
  "data": {
    "added_at": "2015-07-31T10:11:09Z",
    "firmware": "[IGNORE]",
    "location": {
      "city": null,
      "country": null,
      "country_code": null,
      "elevation": null,
      "exposure": null,
      "geohash": null,
      "ip": null,
      "latitude": null,
      "longitude": null
    },
    "recorded_at": "2015-07-31T10:11:09Z",
    "sensors": []
  },
  "description": null,
  "id": 1816,
  "last_reading_at": null,
  "mac_address": "00:0a:95:9d:68:16",
  "name": "my sck",
  "owner": {
    "avatar": "http://images.smartcitizen.me/s100/feca2180/firewatch-4.jpg",
    "device_ids": [
      1816
    ],
    "id": 2997,
    "joined_at": "2015-02-02T15:17:28Z",
    "location": {
      "city": "Barcelona",
      "country": "Spain",
      "country_code": "ES"
    },
    "url": null,
    "username": "john",
    "uuid": "feca2180-d0dd-49fd-8815-ec59ca6d48f6"
  },
  "state": "never_published",
  "system_tags": [
    "new",
    "offline"
  ],
  "updated_at": "2015-07-31T10:11:09Z",
  "uuid": null
}

You must be authenticated to add a device. The currently authenticated user will be registered as the owner of the new device.

Parameter Required? Description
name
string
Name of the device
description
string
Description of the device
exposure
string
Either indoor or outdoor
latitude
decimal
Latitude of the device
longitude
decimal
Longitude of the device

Update a Device

PATCH https://api.smartcitizen.me/v0/devices/:id

http PATCH https://api.smartcitizen.me/v0/devices/1816 access_token=9d00b4c027f757ef1c7b254b9f795d1ebd1e04f7a21b01d5a9dfe5f6e37439b5 description='new description'
HTTP/1.1 200 OK
{
  "added_at": "2015-07-31T10:11:09Z",
  "data": {
    "added_at": "2015-07-31T10:15:06Z",
    "firmware": "[IGNORE]",
    "location": {
      "city": null,
      "country": null,
      "country_code": null,
      "elevation": null,
      "exposure": null,
      "geohash": null,
      "ip": null,
      "latitude": null,
      "longitude": null
    },
    "recorded_at": "2015-07-31T10:15:06Z",
    "sensors": []
  },
  "description": "new description",
  "id": 1816,
  "last_reading_at": null,
  "mac_address": "00:0a:95:9d:68:16",
  "name": "my sck",
  "owner": {
    "avatar": "http://images.smartcitizen.me/s100/feca2180/firewatch-4.jpg",
    "device_ids": [
      1816
    ],
    "id": 2997,
    "joined_at": "2015-02-02T15:17:28Z",
    "location": {
      "city": "Barcelona",
      "country": "Spain",
      "country_code": "ES"
    },
    "url": "http://www.google.com",
    "username": "john",
    "uuid": "feca2180-d0dd-49fd-8815-ec59ca6d48f6"
  },
  "state": "never_published",
  "system_tags": [
    "new",
    "offline"
  ],
  "updated_at": "2015-07-31T10:15:06Z",
  "uuid": "cb480089-c000-4e69-96c0-ad6378f3a537"
}

You must be authenticated and registered as the device's owner if you wish to update a device.

Parameter Example Description
id
integer
2 Unique ID of the device
name
string
Beach SCK Name of the device
description
string
A Smart Citizen on the Beach Description of the device
mac_address
string
00:1C:B3:09:85:15 MAC Address of the device
user_tags
string
A comma-seperated list of tag names more info
exposure
string
Either indoor or outdoor
latitude
decimal
41.401108 Latitude of the device
longitude
decimal
2.215319 Longitude of the device

Remove a Device

DELETE https://api.smartcitizen.me/v0/devices/:id

http DELETE https://api.smartcitizen.me/v0/devices/10
HTTP/1.1 200 OK

You can only delete devices that you own. After a device is deleted with the API there will be a grace period in which you can contact support to reinstate a device if you have removed it in error. After this grace period has passed, the device and its data will be removed permanently from our databases and cannot be restored.

Get All Devices

GET https://api.smartcitizen.me/v0/devices

http GET https://api.smartcitizen.me/v0/devices
HTTP/1.1 200 OK
[
{
  "id": 674,
  "uuid": "a31b92f5-0201-4db4-ac9a-3cfb4a8bbe15",
  "name": "The Continuum",
  "description": "LA CASA",
  "state": "never_published",
  "system_tags": [
    "indoor",
    "offline"
  ],
  "last_reading_at": null,
  "added_at": "2015-02-02T15:59:48Z",
  "updated_at": "2015-05-25T07:31:27Z",
  "mac_address": "[FILTERED]",
  "owner": {
    "id": 498,
    "uuid": "4b09f4d3-040d-4b06-b5e3-8dd10b055dea",
    "username": "Mike6158",
    "avatar": "http://smartcitizen.s3.amazonaws.com/avatars/default.svg",
    "url": null,
    "joined_at": "2015-02-02T15:55:32Z",
    "location": {
      "city": null,
      "country": null,
      "country_code": null
    },
    "device_ids": [
      674
    ]
  },
  "data": {
    "recorded_at": "2015-05-25T07:31:27Z",
    "added_at": "2015-05-25T07:31:27Z",
    "firmware": "[IGNORE]",
    "location": {
      "ip": null,
      "exposure": "indoor",
      "elevation": 348,
      "latitude": 29.7030111,
      "longitude": -96.7805333,
      "geohash": "9v70vxq8d4",
      "city": "Weimar",
      "country_code": "US",
      "country": "United States"
    },
    "sensors": [
      {
        "id": 14,
        "ancestry": null,
        "name": "BH1730FVC",
        "description": "Digital Ambient Light Sensor",
        "unit": "Lux",
        "created_at": "2015-02-02T18:24:56Z",
        "updated_at": "2015-07-05T19:57:36Z",
        "measurement_id": 3,
        "uuid": "ac4234cf-d2b7-4cfa-8765-9f4477e2de5f",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 17,
        "ancestry": null,
        "name": "Battery",
        "description": "Custom Circuit",
        "unit": "%",
        "created_at": "2015-02-02T18:26:28Z",
        "updated_at": "2015-07-05T19:55:34Z",
        "measurement_id": 7,
        "uuid": "5b0e390e-781d-4243-8e97-579eead09792",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 13,
        "ancestry": "19",
        "name": "HPP828E031",
        "description": "Humidity",
        "unit": "%",
        "created_at": "2015-02-02T18:24:30Z",
        "updated_at": "2015-07-05T19:54:54Z",
        "measurement_id": 2,
        "uuid": "1c19ae8f-b995-460f-87a3-a9d0c140abfb",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 12,
        "ancestry": "19",
        "name": "HPP828E031",
        "description": "Temperature",
        "unit": "ºC",
        "created_at": "2015-02-02T18:24:02Z",
        "updated_at": "2015-07-05T19:55:07Z",
        "measurement_id": 1,
        "uuid": "2922d20e-3b83-4d98-8791-cfcdfc12fa99",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 15,
        "ancestry": "20",
        "name": "MiCS-4514",
        "description": "NO2",
        "unit": "kOhm/ppm",
        "created_at": "2015-02-02T18:25:51Z",
        "updated_at": "2015-07-05T19:57:59Z",
        "measurement_id": 6,
        "uuid": "0c5b7e74-ef87-431d-89af-dd51de84b10e",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 16,
        "ancestry": "20",
        "name": "MiCS-4514",
        "description": "CO",
        "unit": "kOhm/ppm",
        "created_at": "2015-02-02T18:26:11Z",
        "updated_at": "2015-07-05T19:58:18Z",
        "measurement_id": 5,
        "uuid": "49a26be4-3ce1-4f2e-a09b-4296fefcfe17",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 21,
        "ancestry": null,
        "name": "Microchip RN-131",
        "description": "802.11 b/g WiFi",
        "unit": "# networks",
        "created_at": "2015-05-04T11:17:18Z",
        "updated_at": "2015-07-05T19:57:22Z",
        "measurement_id": 9,
        "uuid": "5b1f0e38-336a-4abf-9989-69b48f0026ef",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 7,
        "ancestry": null,
        "name": "POM-3044P-R",
        "description": "Electret microphone with envelope follower sound pressure sensor (noise)",
        "unit": "dB",
        "created_at": "2015-02-02T18:16:41Z",
        "updated_at": "2015-07-05T19:56:59Z",
        "measurement_id": 4,
        "uuid": "5efd2376-6783-476b-bf85-57ead5f89654",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      },
      {
        "id": 18,
        "ancestry": null,
        "name": "Solar Panel",
        "description": "Custom Circuit",
        "unit": "mV",
        "created_at": "2015-02-02T18:26:40Z",
        "updated_at": "2015-07-05T19:54:35Z",
        "measurement_id": 8,
        "uuid": "95d59a95-3791-423c-a201-b19c327765d8",
        "value": null,
        "raw_value": null,
        "prev_value": null,
        "prev_raw_value": null
      }
    ]
  },
  "kit": {
    "id": 3,
    "uuid": "6ae30424-4e09-4318-b96d-771996657c70",
    "slug": "sck:1,1",
    "name": "SCK 1.1 - Ambient Board",
    "description": "Kickstarter Board",
    "created_at": "2015-02-02T18:23:16Z",
    "updated_at": "2015-05-25T14:06:46Z"
  }
}
...

Returns all devices, with the same data as above.

Parameter Example Description
near
string
(lat,lng)
41.401108,
2.215319
When included, returns devices in order of distance from the coordinates

World Map of Devices

GET https://api.smartcitizen.me/v0/devices/world_map

http GET https://api.smartcitizen.me/v0/devices/world_map
HTTP/1.1 200 OK
[
{
  "id": 1630,
  "name": "IONIAN UNIVERSITY SMART CITIZEN PROJECT TEST ",
  "description": "SMART CITIZEN SENSORS BOARD",
  "owner_id": 2278,
  "owner_username": "gvlachos",
  "latitude": 39.6249838,
  "longitude": 19.9223461,
  "city": "Kérkira",
  "country_code": "GR",
  "kit_id": 3,
  "state": "has_published",
  "system_tags": [
    "indoor",
    "offline"
  ],
  "exposure": "indoor",
  "data": {
    "": "2015-06-25T07:45:03Z",
    "7": 66.875,
    "12": 20.24169189453124,
    "13": 70.262939453125,
    "14": 290.9,
    "15": 20.965,
    "16": 558.478,
    "17": 100.0,
    "18": 4128,
    "21": 2,
    "7_raw": 255,
    "12_raw": 27316,
    "13_raw": 33168,
    "14_raw": 2909,
    "15_raw": 20965,
    "16_raw": 558478,
    "17_raw": 1000,
    "18_raw": 4128
  },
  "added_at": "2015-02-02T15:59:51Z"
}
...

Returns an array with of summarized device objects for displaying on the world map.

Field Example Description
id*
integer
1619 Incremental, unique ID of the device
name
string
My amazing sensor Name of the device
description
string
An SCK in Southwark Description of the device
state
string
"has_published" (Automatic) state of the device. See state.
system_tags
string array
['new', 'indoor'] See system_tag values table below.
user_tags
string array
['new', 'indoor'] An Array of user tags, predefined from a specific list available in tags.
last_reading_at*
datetime
"2015-04-30T17:56:04.432Z" Last reading from any of the sensors of the device.
location
location
See location Object containing device's location
hardware
hardware
See hardware Object containing device's hardware information

Sensors

Every device has sensor(s). A sensor is something on a device that can record data. This could be anything: temperature, noise, humidity, voltage...

Get all Sensors

GET https://api.smartcitizen.me/v0/sensors

http GET https://api.smartcitizen.me/v0/sensors

HTTP/1.1 200 OK
[
{
  "id": 3,
  "uuid": "ac284ba3-e2fc-4795-b2b1-530b32a9b05b",
  "parent_id": null,
  "name": "DHT22",
  "description": "A digital temperature and humidity sensor. It uses a capacitive humidity sensor and a thermistor to measure the surrounding air, and spits out a digital signal on the data pin (no analog input pins needed)",
  "unit": null,
  "created_at": "2015-02-02T18:14:15Z",
  "updated_at": "2015-02-02T18:14:15Z"
}
...

Since real-world sensors can contain multiple sub-sensors. For instance, the Sensirion SHT31 records temperature and humidity, in a single package. To represent this, we use the concept of parent. If a sensor has a parent then it is a sub-sensor. You can find which sensor a sub-sensors belongs to with the parent_id.

Parameter Description
id*
integer
Autoincrementing unique ID for the sensor
uuid*
uuid
Unique ID for the sensor
parent_id*
integer
ID of the parent (null if none)
name
string
Name of the sensor
description
string
Description of the sensor
datasheet
string
Link to the sensor datasheet
unit
string
The unit of measurement for readings recorded with the sensor
unit_definition
string
Link to the vocabulary for the unit
measurement
measurement
Measurement taken with the sensor
tags
sensortag
Sensor tag
created_at*
datetime
When the sensor was added to the platform
updated_at*
datetime
When the sensor was updated on the platform

Get a single Sensor

GET https://api.smartcitizen.me/v0/sensors/:id

http GET https://api.smartcitizen.me/v0/sensors/5

HTTP/1.1 200 OK
{
  "id": 5,
  "uuid": "6b4b64d9-3841-446c-a7f5-63f480932b96",
  "parent_id": 3,
  "name": "DHT22 - Humidity",
  "description": "Humidity",
  "unit": "%",
  "created_at": "2015-02-02T18:15:34Z",
  "updated_at": "2015-07-05T19:53:22Z",
  "measurement": {
    "id": 2,
    "uuid": "9cbbd396-5bd3-44be-adc0-7ffba778072d",
    "name": "relativee humidity",
    "description": "Relative humidity is a measure of the amount of moisture in the air relative to the total amount of moisture the air can hold. For instance, if the relative humidity was 50%, then the air is only half saturated with moisture."
  }
}

Will return same parameters as above, but for a single sensor.

Readings

Get Latest Readings

GET https://api.smartcitizen.me/v0/devices/:id

http GET https://api.smartcitizen.me/v0/devices/1616
HTTP/1.1 200 OK
{
  "id": 1616,
  "uuid": "85543ca2-e543-4351-9122-98756d50e6b1",
  "name": "Orchid Surf Stay Bali",
  "description": "Located at the pool area of the hotel ",
  "state": "has_published",
  "system_tags": [
    "offline",
    "outdoor"
  ],
  "last_reading_at": "2015-07-16T08:53:16Z",
  "added_at": "2015-02-02T15:59:51Z",
  "updated_at": "2015-07-16T08:53:32Z",
  "mac_address": "[FILTERED]",
  "owner": {
    "id": 2247,
    "uuid": "bcd5b918-d89f-4cb6-a2bb-30245904bc2f",
    "username": "JesusZabala",
    "avatar": "http://smartcitizen.s3.amazonaws.com/avatars/default.svg",
    "url": null,
    "joined_at": "2015-02-02T15:55:41Z",
    "location": {
      "city": null,
      "country": null,
      "country_code": null
    },
    "device_ids": [
      1616
    ]
  },
  "data": {
    "recorded_at": "2015-07-16T08:53:32Z",
    "added_at": "2015-07-16T08:53:32Z",
    "firmware": "[IGNORE]",
    "location": {
      "ip": null,
      "exposure": "outdoor",
      "elevation": 1,
      "latitude": -8.82111778712582,
      "longitude": 115.15258114151,
      "geohash": "qw3vu65t38",
      "city": "Kuta Selatan",
      "country_code": "ID",
      "country": "Indonesia"
    },
    "sensors": [
      {
        "id": 10,
        "ancestry": null,
        "name": "Battery",
        "description": "Custom Circuit",
        "unit": "%",
        "created_at": "2015-02-02T18:18:00Z",
        "updated_at": "2015-07-05T19:53:51Z",
        "measurement_id": 7,
        "uuid": "c9ff2784-53a7-4a84-b0fc-90ecc7e313f9",
        "value": 100.0,
        "raw_value": 1000,
        "prev_value": 100.0,
        "prev_raw_value": 1000
      },
      {
        "id": 5,
        "ancestry": "3",
        "name": "DHT22 - Humidity",
        "description": "Humidity",
        "unit": "%",
        "created_at": "2015-02-02T18:15:34Z",
        "updated_at": "2015-07-05T19:53:22Z",
        "measurement_id": 2,
        "uuid": "6b4b64d9-3841-446c-a7f5-63f480932b96",
        "value": 1.0,
        "raw_value": 10,
        "prev_value": 1.0,
        "prev_raw_value": 10
      },
      {
        "id": 4,
        "ancestry": "3",
        "name": "DHT22 - Temperature",
        "description": "Temperature",
        "unit": "ºC",
        "created_at": "2015-02-02T18:15:14Z",
        "updated_at": "2015-07-05T19:53:02Z",
        "measurement_id": 1,
        "uuid": "a50dbd88-b0c7-4094-ad74-2b755e8023a8",
        "value": 29.8,
        "raw_value": 298,
        "prev_value": 29.9,
        "prev_raw_value": 299
      },
      {
        "id": 8,
        "ancestry": null,
        "name": "MICS-2710",
        "description": "MOS NO2 gas sensor",
        "unit": "kOhm (ppm)",
        "created_at": "2015-02-02T18:17:23Z",
        "updated_at": "2015-07-05T19:56:21Z",
        "measurement_id": 6,
        "uuid": "1eb0249d-29d8-41be-8e24-d3b1e5773c0f",
        "value": 197.574,
        "raw_value": 197574,
        "prev_value": 182.971,
        "prev_raw_value": 182971
      },
      {
        "id": 9,
        "ancestry": null,
        "name": "MICS-5525",
        "description": "MOS CO gas sensor",
        "unit": "kOhm (ppm)",
        "created_at": "2015-02-02T18:17:44Z",
        "updated_at": "2015-07-05T19:56:07Z",
        "measurement_id": 5,
        "uuid": "7baaecb7-2586-4063-9c15-bfa999e329aa",
        "value": 276.753,
        "raw_value": 276753,
        "prev_value": 278.468,
        "prev_raw_value": 278468
      },
      {
        "id": 21,
        "ancestry": null,
        "name": "Microchip RN-131",
        "description": "802.11 b/g WiFi",
        "unit": "# networks",
        "created_at": "2015-05-04T11:17:18Z",
        "updated_at": "2015-07-05T19:57:22Z",
        "measurement_id": 9,
        "uuid": "5b1f0e38-336a-4abf-9989-69b48f0026ef",
        "value": 4,
        "raw_value": null,
        "prev_value": 4,
        "prev_raw_value": null
      },
      {
        "id": 7,
        "ancestry": null,
        "name": "POM-3044P-R",
        "description": "Electret microphone with envelope follower sound pressure sensor (noise)",
        "unit": "dB",
        "created_at": "2015-02-02T18:16:41Z",
        "updated_at": "2015-07-05T19:56:59Z",
        "measurement_id": 4,
        "uuid": "5efd2376-6783-476b-bf85-57ead5f89654",
        "value": 67.2,
        "raw_value": 31,
        "prev_value": 59.8,
        "prev_raw_value": 13
      },
      {
        "id": 6,
        "ancestry": null,
        "name": "PVD-P8001",
        "description": "LDR Analog Light Sensor",
        "unit": "%",
        "created_at": "2015-02-02T18:15:55Z",
        "updated_at": "2015-07-05T19:56:43Z",
        "measurement_id": 3,
        "uuid": "0e9cdc5b-d369-4480-9676-bf31af6a5977",
        "value": 1.5,
        "raw_value": 15,
        "prev_value": 1.7,
        "prev_raw_value": 17
      },
      {
        "id": 11,
        "ancestry": null,
        "name": "Solar Panel",
        "description": "Custom Circuit",
        "unit": "mV",
        "created_at": "2015-02-02T18:18:12Z",
        "updated_at": "2015-07-05T19:54:09Z",
        "measurement_id": 8,
        "uuid": "4ab402c5-9297-407a-b0b2-7089520f7ed0",
        "value": 5.066,
        "raw_value": 5066,
        "prev_value": 5.067,
        "prev_raw_value": 5067
      }
    ]
  },
  "kit": {
    "id": 2,
    "uuid": "1409dba9-b06b-4ea5-904c-e0df6e09b903",
    "slug": "sck:1,0",
    "name": "SCK 1.0 - Ambient Board",
    "description": "Goteo Board",
    "created_at": "2015-02-02T18:18:50Z",
    "updated_at": "2015-05-25T14:06:25Z"
  }
}

(for a device)

The latest set of readings is included with the device, so if you call /v0/devices/:id you will see the most recent set of readings embedded in data.sensors as value and raw_value.

Get Historical Readings

GET https://api.smartcitizen.me/v0/devices/:device_id/readings

http GET https://api.smartcitizen.me/v0/devices/1616/readings?sensor_id=7&rollup=4h&from=2015-07-28&to=2015-07-30
HTTP/1.1 200 OK
{
  "device_id": 1616,
  "sensor_id": 7,
  "rollup": "4h",
  "function": "avg",
  "from": "2015-07-28T00:00:00Z",
  "to": "2015-07-30T00:00:00Z",
  "sample_size": 1776,
  "readings": [
    [
      "2015-07-29T20:00:35Z",
      65.78151658767773
    ],
    [
      "2015-07-29T16:00:46Z",
      65.67438423645321
    ],
    [
      "2015-07-29T12:00:06Z",
      65.88564593301437
    ],
    [
      "2015-07-29T08:00:07Z",
      65.86494845360832
    ],
    [
      "2015-07-29T04:00:36Z",
      65.47640791476408
    ],
    [
      "2015-07-29T00:00:12Z",
      64.98706140350879
    ],
    [
      "2015-07-28T20:00:38Z",
      63.82850241545894
    ],
    [
      "2015-07-28T16:00:03Z",
      65.36859903381644
    ],
    [
      "2015-07-28T14:14:05Z",
      65.28877551020409
    ]
  ]
}

Returns the readings that were recorded for a specific sensor on a device.

Readings are returned as a tuple [recorded_at, value]

Request Parameters

Parameter Example Required? Description
device_id
integer
2 Unique ID of the device
sensor_id
integer
7 Unique ID of the sensor on the device
rollup
string
1w (1 week) Timespan to use when grouping readings. See table
from
datetime
2015-07-20 00:00:00 UTC The start of the range of readings
to
datetime
2015-07-27 00:00:00 UTC The end of the range of readings
function
string
avg Method to use when grouping the readings. See table
all_intervals
boolean
true Include all possible timestamps within the from > to range, even if they have nil values

Response

Field Description
device_id
integer
Unique ID of the device
rollup
string
Timespan of data groups
function
string
How the readings collection should be grouped
from
datetime
The beginning of the timeframe
from
datetime
The end of the timeframe
sample_size
integer
The count of readings that were examined to build the response
readings
array
Array of tuples, representing the recorded_at and value of each reading

Rollup measurements

key value
y years
M months
w weeks
d days
h hours
m minutes
s seconds
ms milliseconds

Functions

Parameter Description
avg Computes average readings within the rollup period
max Returns the largest readings within the rollup period
min Returns the smallest readings within the rollup period
sum  Sums all readings within the rollup period
count Counts the number of readings within rollup periods
dev Computes standard deviation
first Returns the first readings within the rollup period
last Returns the last readings within the rollup period

CSV Archive of readings

GET https://api.smartcitizen.me/v0/devices/:id/readings/csv_archive

access_token authentication required, you must either be the owner of the device or an admin.

possible responses:

Error Code Meaning
200 OK, job has been enqueued and the user will be emailed a link to the CSV file
401 Unauthorised
403 Forbidden
404 Device not found
420 (rate limiting, please only make one request every X -- currently X = 6 hours)
500 Server Error

If you try to GET the endpoint multiple times you will receive a 420 rate limit error until 6 hours have passed.

Post Readings

A device has one Blueprint we call kit, and a blueprint has many sensors through components.

Most devices on the platform share the same blueprint, a default SCK 1.1 (e.g. Kickstarter Board). But new devices (e.g. Raspberry Pi's, new Sensor Add-ons) might use a different Blueprints.

GET https://api.smartcitizen.me/v0/devices/:device_id/readings

access_token authentication required, you must either be the owner of the device or an admin.

http POST https://api.smartcitizen.me/v0/devices/1816/readings?access_token=xxxxxxxxxxx
{
  "data": [{
    "recorded_at": "2016-06-08 10:30:00",
    "sensors": [{
      "id": 22,
      "value": 21
    }]
  }]
}
{
  "data": [{
    "recorded_at": "2016-06-08 10:30:00",
    "sensors": [{
      "id": "temp",
      "value": 21
    }]
  }]
}

Request Parameters

Parameter Example Required? Description
data
array
The data payload

Data Parameters

Parameter Example Required? Description
recorded_at
datetime
2015-07-20 00:00:00 UTC The time when the reading took place
sensors
array
The sensors objects

Sensor Parameters

Parameter Example Required? Description
id
integer
12 The id
id
string
temp Instead of the id we can use a hash as defined on the Blueprint
value
float
22 The value of the sensor (can be an integer or float)

Measurements

Measurements help us understand what Sensors are recording.

Get All Measurements

GET https://api.smartcitizen.me/v0/measurements

http GET https://api.smartcitizen.me/v0/measurements
HTTP/1.1 200 OK
[
{
  "id": 1,
  "uuid": "b3f44b63-0a17-4d84-bbf1-4c17764b7eae",
  "name": "air temperature",
  "description": "Air temperature is a measure of how hot or cold the air is. It is the most commonly measured weather parameter. Air temperature is dependent on the amount and strength of the sunlight hitting the earth, and atmospheric conditions, such as cloud cover and humidity, which trap heat.",
  "created_at": "2015-07-03T10:16:10Z",
  "updated_at": "2015-07-03T10:16:10Z"
}
...
Parameter Description
id*
integer
Autoincrementing unique ID for the measurement
uuid*
uuid
Unique ID for the measurement
name
string
Name of the measurement
description
string
Description of the measurement
definition
string
Link to a vocabulary defining the measurement
created_at*
datetime
When the measurement was added to the platform
updated_at*
datetime
When the measurement was updated on the platform

Get a single Measurement

GET https://api.smartcitizen.me/v0/measurements/:id

GET https://api.smartcitizen.me/v0/measurements/2
HTTP/1.1 200 OK
{
  "id": 2,
  "uuid": "9cbbd396-5bd3-44be-adc0-7ffba778072d",
  "name": "relativee humidity",
  "description": "Relative humidity is a measure of the amount of moisture in the air relative to the total amount of moisture the air can hold. For instance, if the relative humidity was 50%, then the air is only half saturated with moisture.",
  "created_at": "2015-07-03T10:16:23Z",
  "updated_at": "2015-07-03T10:16:23Z"
}

Components

Components are used to join Devices to Sensors. These are not accessible via the API, but are documented here for reference in case you deploy the platform yourself.

Field Description
id*
integer
Autoincrementing unique ID for the component
uuid*
uuid
Unique ID for the component
device_id*
integer
ID of the Device that the component is associated with
sensor_id*
integer
ID of the Sensor that the component is associated with
created_at*
datetime
When the component was added to the platform
updated_at*
datetime
When the component was updated on the platform

Experiments

Experiments are collection of devices that represent a real-world-experiment by a user or group of users. This is currently a experimental feature.

Get an experiment

GET https://api.smartcitizen.me/v0/experiment/:id

Returns a single experiment.

Field Example Description
id*
integer
1 Incremental, unique ID of the experiment
name
string
My experiment Name of the experiment
description
string
Deployment of sensors Description of the deviexperimentce
owner_id*
int
See owner Experiment's owner ID
active*
bool
True If the experiment is active or not, derived from starts_at and ends_at
starts_at*
datetime
"2015-04-30T17:56:04.432Z" When the experiment started.
ends_at*
datetime
"2015-04-30T17:56:04.432Z" When the experiment finished.
device_ids*
Array
[19, 149, 2902] Array of devices IDs
created_at*
datetime
"2015-04-30T17:56:04.432Z" When the experiment was created in the platform.
updated_at*
datetime
"2015-04-30T17:56:04.432Z" When the experiment info was last updated.

Add an Experiment

POST https://api.smartcitizen.me/v0/experiment

You must be authenticated to add an experiment. The currently authenticated user will be registered as the owner of the new experiment.

Parameter Required? Description
name
string
Name of the experiment
description
string
Description of the experiment.
starts_at*
datetime
When the experiment started.
ends_at*
datetime
When the experiment finished.
device_ids*
Array
Array of devices IDs. Not necessarily owned by the owner of the experiment.

Update an experiment

PATCH https://api.smartcitizen.me/v0/experiment/:id

You must be authenticated and registered as the experiment's owner if you wish to update an experiment. See Add an experiment.

Remove an experiment

DELETE https://api.smartcitizen.me/v0/experiment/:id

You can only delete experiments that you own. Deleting an experiment, doesn't delete the devices associated with them.

Get All Experiments

GET https://api.smartcitizen.me/v0/experiments

Returns all experiments, with the same data as above.

Tags

Tags are used on devices to group them in flexible ways.

Get all Tags

GET https://api.smartcitizen.me/v0/tags

GET https://api.smartcitizen.me/v0/tags

HTTP/1.1 200 OK
[
{
  "id": 1,
  "uuid": "f7f09e83-9da9-431b-9be2-cc411f40afbf",
  "name": "testtag",
  "description": "test description"
}
...
Parameter Example Description
id
integer
2 Unique ID of the tag
name
string
example-tag Unique name of the tag [A-Za-z0-9-_]
description
string
Further information about the tag
created_at*
datetime
When the tag was added to the platform
updated_at*
datetime
When the tag was updated on the platform

Adding/editing a device's tags

PATCH https://api.smartcitizen.me/v0/devices/:id

Include comma seperated list of tag names in user_tags property.

For example, if there are tags with the names interesting and cool-hardware you could add these tags to a device by PATCHING user_tags = 'interesting,cool-hardware'.

If you then wanted to remove cool-hardware you would PATCH again, but without the second tag i.e. user_tags = interesting.

Creating a Tag

POST https://api.smartcitizen.me/v0/tags Admin only

Updating a Tag

PATCH https://api.smartcitizen.me/v0/tags/:id Admin only

Deleting a Tag

DELETE https://api.smartcitizen.me/v0/tags/:id Admin only

Sensor Tags

Sensor tags are not available via the API. This documentation is included only for reference.

Sometimes, it's useful to associate tags to sensors, to make it easier to understand what the are. For instance, a Carbon monoxide sensor may record voltages, and we may want to consider those readings as raw. This is represented with SensorTags. However, since voltage can be also used for measuring electric properties, we use these tags, and not other ad-hoc measurements to avoid duplication.

Response Status Codes

Error Messages

HTTP/1.1 404 Not Found
{
  "id" : "record_not_found",
  "message" : "Couldn't find Device with 'id'=101308",
  "errors": null,
  "url" : null
}


HTTP/1.1 422 Unprocessable Entity
{
  "id": "unprocessable_entity",
  "message": "Unprocessable Entity",
  "errors": {
    "mac_address": [
      "can't be blank",
      "is invalid"
    ],
    "name": [
      "can't be blank"
    ]
  },
  "url": null
}

When possible, read the HTTP status codes to learn of the success of your request. The API uses the following pattern for error messages, as recommended by https://github.com/interagent/http-api-design.

Success Codes

Code Meaning
200 Request succeeded for a GET call, for a DELETE or PATCH call that completed synchronously, or for a PATCH call that synchronously updated an existing resource
201 Request succeeded for a POST call that completed synchronously, or for a PATCH call that synchronously created a new resource

Error Codes

Code Meaning
400 Bad Request -- there is a problem with your request
401 Unauthorized -- Your authentication credentials are incorrect
403 Forbidden -- The resource requested is hidden, or you do not have the necessary privileges
404 Not Found -- The specified resource could not be found
405 Method Not Allowed -- You tried to access a resource with an invalid method
406 Not Acceptable -- You requested a format that isn't json
422 Unprocessable Entity: Your request was understood, but contained invalid parameters
429 Too Many Requests
500 Internal Server Error
503 Service Unavailable -- We're temporarially offline for maintanance. Please try again later

Real Time

Websockets

The real time API uses websockets to push devices information in real-time and it is based on the famous socket.io library. We support WSS, WebSockets over SSL/TLS, like HTTPS. We also support fallback to long polling for older browsers.

data-received is currently the only available topic. Everytime a device publishes data to the platform data is pushed over the channel. With the same model as device GET.

#See the javascript section
io.connect('wss://ws.smartcitizen.me').on('data-received', doSomething);
  
    <html>
     <head>
      <script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/1.4.6/socket.io.js"></script>
      <style>
        body {
          font-family: Helvetica, Arial, sans-serif;
          color: white;
          font-weight: bold;
        }
        div {
          float: left;
          display: block;
          background: #4FC9E8!important;
          margin: 5px;
          width: 100px;
          padding: 5px;
          height: 100px;
        }
      </style>
      <script>
        io.connect('wss://ws.smartcitizen.me')
        .on('data-received',
         function(device) {
            document.body.innerHTML = document.body.innerHTML
            + "<div>" + device.data.name + "</div>"
         });
      </script>
     </head>
     <body>
     </body>
    </html>
  
  Live demo: http://codepen.io/pral2a/pen/jrPNzy

Data forwarding

MQTT

Instead of using websockets, you can also use MQTT, to get rendered data from the devices in real-time. This can help into bringing MQTT features such as persistent sessions and allow for a more robust data ingestion. We support MQTT/s, MQTT over SSL/TLS, like HTTPS. Everytime a device publishes data to the platform data is pushed over, with the same model as device GET.

MQTT forwarding is only enabled if the user is a researcher (see users) and if they have enabled forwarding on their device. See data policy on the device section. You need to collect your forwarding_username and forwarding_token secrets from the users endpoint after an authenticated request.

# You will need mosquitto (and mosquitto_sub) for this
mosquitto_sub -h mqtt.smartcitizen.me -u '<forwarding_username>' -t '/forward/<forwarding_token>/device/<device_id>/readings' -v

# You can get all the devices from a user
mosquitto_sub -h mqtt.smartcitizen.me -u '<forwarding_username>' -t '/forward/<forwarding_token>/device/+/readings' -v

# Note that wildcard topics at the /forward level are not allowed

Onboarding

Start onboarding process

POST https://api.smartcitizen.me/v0/onboarding/device

http POST https://api.smartcitizen.me/v0/onboarding/device

HTTP/1.1 200 OK
[
{
  "onboarding_session": "a562f6bb-4328-4d5b-bb9f-ea6bd8e592a8",
  "device_token": "d803e0"

}
...

Method creates orphan_device and returns unique onboarding_session and device_token.

Requires no params at all, however, it can take any of the following: name, description, kit_id, exposure, latitude, longitude, user_tags.

Any passed params will be used on the creation of the orphan_device.

Note that both device_token and onboarding_session are unique for each orphan_device.

Parameter Description
name
string
Name of the device
description
string
Description of the device
kit_id
integer
Unique ID of the kit for the device
exposure
string
Either indoor or outdoor
latitude
decimal
Latitude of the device
longitude
decimal
Longitude of the device
user_tags
string
A comma-seperated list of tag names more info

Update orphan_device

PATCH https://api.smartcitizen.me/v0/onboarding/device

Method to update (slide by slide, or all at once) the still 'orphan' device. It requires a valid 'Onboarding-Session' header and returns updated 'orphan_device' (status 200) if successfully updated.

Calling without an existent 'Onboarding-Session' returns error "Invalid onboarding_session" (404).

#bash
curl -XPATCH 'https://api.smartcitizen.me/v0/onboarding/device' -H "OnboardingSession: d049c9e7-0261-49e4-91be-8a0bafa1c8b9"

Find existing user

POST https://api.smartcitizen.me/v0/onboarding/user

Method that requires params 'email' and returns user 'username' if email is associated to an existent user (status 200). If 'email' does not correspond to any user (404) not_found is returned.

Calling without 'email' params results in a 422, "Missing Params".

#bash
curl -XPOST 'https://api.smartcitizen.me/v0/onboarding/user?email=user1@test.com'
# Post:
{
  "email": "user1@email.com"
}
# Response:
{
  "username": "user1"
}

User login

In order to complete the 'Onboarding Process', it is required user authentication.

Register device

POST https://api.smartcitizen.me/v0/onboarding/register

Method adds to the current_user a new device using onboarding_session's correspondent orphan_device attributes.

#bash
curl -XPOST 'https://api.smartcitizen.me/v0/onboarding/register?access_token=abcdefghijk' -H "OnboardingSession: d049c9e7-0261-49e4-91be-8a0bafa1c8b9"
{
  "id": 1,
  "owner_id": 2,
  "name": "OrphanDeviceName",
  "description": "OrphanDeviceDescription",
  "mac_address": nil,
  "latitude": 41.3966908,
  "longitude": 2.1921909,
  "created_at": "2016-10-29T12:31:25+02:00",
  "updated_at": "2016-10-29T12:31:25+02:00",
  "kit_id": 1,
  "latest_data": nil,
  "geohash": "sp3e9bh31y",
  "last_recorded_at": nil,
  "meta": {
    "exposure": "indoor"
  },
  "location": {
    "address": "Carrer de Pallars, 122, 08018 Barcelona, Barcelona, Spain",
    "city": "Barcelona",
    "postal_code": "08018",
    "state_name": "Catalunya",
    "state_code": "CT",
    "country_code": "ES"
  },
  "data": nil,
  "old_data": nil,
  "owner_username": "user2",
  "uuid": nil,
  "migration_data": nil,
  "workflow_state": "active",
  "csv_export_requested_at": nil,
  "old_mac_address": nil,
  "state": "not_configured"
}

This is the end of the onboarding process.