Your First API Request
This guide walks you through making your first API request to dakkio, from authentication to data ingestion.
Before You Start
Make sure you have:
- ✅ A dakkio account
- ✅ A bucket created
- ✅ A data source configured
- ✅ An API key generated
If not, follow the Quick Start guide first.
Step-by-Step Example
We'll build a complete example of ingesting temperature data from an IoT sensor.
1. Prepare Your Environment
Set up your API key as an environment variable:
export DAKKIO_API_KEY="dakkio_a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6"
export BUCKET_ID="507f1f77bcf86cd799439011"
export DATA_SOURCE_ID="507f1f77bcf86cd799439012"
2. Test Your API Key
Verify your API key works by querying your bucket:
curl -X POST https://api.dakkio.io/api/data/query \
-H "X-API-Key: $DAKKIO_API_KEY" \
-H "Content-Type: application/json" \
-d "{
\"bucketId\": \"$BUCKET_ID\",
\"filters\": {
\"limit\": 1
}
}"
Expected Response:
{
"data": [],
"metadata": {
"count": 0
}
}
If you see this, your API key is valid! (Empty data is normal for a new bucket)
3. Send a Single Data Point
Now let's send your first temperature reading:
curl -X POST https://api.dakkio.io/api/data \
-H "X-API-Key: $DAKKIO_API_KEY" \
-H "Content-Type: application/json" \
-d "{
\"bucketId\": \"$BUCKET_ID\",
\"dataSourceId\": \"$DATA_SOURCE_ID\",
\"timestamp\": \"$(date -u +%Y-%m-%dT%H:%M:%SZ)\",
\"values\": {
\"temperature\": 22.5,
\"humidity\": 65
},
\"metadata\": {
\"location\": \"Living Room\",
\"deviceId\": \"ESP32-001\"
}
}"
Expected Response:
{
"message": "Data point ingested successfully",
"dataPoint": {
"_id": "507f1f77bcf86cd799439016",
"timestamp": "2024-01-15T10:30:00Z",
"values": {
"temperature": 22.5,
"humidity": 65
}
}
}
🎉 Success! You just sent your first data point to dakkio!
4. Send Multiple Data Points
For better efficiency, send multiple readings at once:
curl -X POST https://api.dakkio.io/api/data/batch \
-H "X-API-Key: $DAKKIO_API_KEY" \
-H "Content-Type: application/json" \
-d "{
\"bucketId\": \"$BUCKET_ID\",
\"dataPoints\": [
{
\"dataSourceId\": \"$DATA_SOURCE_ID\",
\"timestamp\": \"2024-01-15T10:00:00Z\",
\"values\": { \"temperature\": 22.0, \"humidity\": 68 }
},
{
\"dataSourceId\": \"$DATA_SOURCE_ID\",
\"timestamp\": \"2024-01-15T10:05:00Z\",
\"values\": { \"temperature\": 22.2, \"humidity\": 67 }
},
{
\"dataSourceId\": \"$DATA_SOURCE_ID\",
\"timestamp\": \"2024-01-15T10:10:00Z\",
\"values\": { \"temperature\": 22.5, \"humidity\": 65 }
}
]
}"
Expected Response:
{
"message": "Batch data ingested successfully",
"insertedCount": 3
}
5. Query Your Data
Retrieve the data you just sent:
curl -X POST https://api.dakkio.io/api/data/query \
-H "X-API-Key: $DAKKIO_API_KEY" \
-H "Content-Type: application/json" \
-d "{
\"bucketId\": \"$BUCKET_ID\",
\"filters\": {
\"dataSourceIds\": [\"$DATA_SOURCE_ID\"],
\"startTime\": \"2024-01-15T00:00:00Z\",
\"endTime\": \"2024-01-15T23:59:59Z\"
},
\"limit\": 10
}"
Expected Response:
{
"data": [
{
"timestamp": "2024-01-15T10:00:00Z",
"values": { "temperature": 22.0, "humidity": 68 }
},
{
"timestamp": "2024-01-15T10:05:00Z",
"values": { "temperature": 22.2, "humidity": 67 }
},
{
"timestamp": "2024-01-15T10:10:00Z",
"values": { "temperature": 22.5, "humidity": 65 }
}
],
"metadata": {
"count": 3
}
}
Code Examples
JavaScript/Node.js
const axios = require('axios');
const API_KEY = process.env.DAKKIO_API_KEY;
const BUCKET_ID = process.env.BUCKET_ID;
const DATA_SOURCE_ID = process.env.DATA_SOURCE_ID;
async function sendData() {
try {
const response = await axios.post(
'https://api.dakkio.io/api/data',
{
bucketId: BUCKET_ID,
dataSourceId: DATA_SOURCE_ID,
timestamp: new Date().toISOString(),
values: {
temperature: 22.5,
humidity: 65
},
metadata: {
location: 'Living Room',
deviceId: 'ESP32-001'
}
},
{
headers: {
'X-API-Key': API_KEY,
'Content-Type': 'application/json'
}
}
);
console.log('Success:', response.data);
} catch (error) {
console.error('Error:', error.response.data);
}
}
sendData();
Python
import requests
import os
from datetime import datetime
API_KEY = os.environ['DAKKIO_API_KEY']
BUCKET_ID = os.environ['BUCKET_ID']
DATA_SOURCE_ID = os.environ['DATA_SOURCE_ID']
def send_data():
response = requests.post(
'https://api.dakkio.io/api/data',
headers={
'X-API-Key': API_KEY,
'Content-Type': 'application/json'
},
json={
'bucketId': BUCKET_ID,
'dataSourceId': DATA_SOURCE_ID,
'timestamp': datetime.utcnow().isoformat() + 'Z',
'values': {
'temperature': 22.5,
'humidity': 65
},
'metadata': {
'location': 'Living Room',
'deviceId': 'ESP32-001'
}
}
)
if response.status_code == 201:
print('Success:', response.json())
else:
print('Error:', response.json())
send_data()
Arduino/ESP32
#include <WiFi.h>
#include <HTTPClient.h>
#include <ArduinoJson.h>
const char* ssid = "YOUR_WIFI_SSID";
const char* password = "YOUR_WIFI_PASSWORD";
const char* apiKey = "dakkio_a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6";
const char* bucketId = "507f1f77bcf86cd799439011";
const char* dataSourceId = "507f1f77bcf86cd799439012";
void sendData(float temperature, float humidity) {
if (WiFi.status() == WL_CONNECTED) {
HTTPClient http;
http.begin("https://api.dakkio.io/api/data");
http.addHeader("Content-Type", "application/json");
http.addHeader("X-API-Key", apiKey);
StaticJsonDocument<256> doc;
doc["bucketId"] = bucketId;
doc["dataSourceId"] = dataSourceId;
doc["timestamp"] = "2024-01-15T10:30:00Z"; // Use RTC or NTP
JsonObject values = doc.createNestedObject("values");
values["temperature"] = temperature;
values["humidity"] = humidity;
String payload;
serializeJson(doc, payload);
int httpCode = http.POST(payload);
if (httpCode == 201) {
Serial.println("Data sent successfully!");
} else {
Serial.printf("Error: %d\n", httpCode);
}
http.end();
}
}
void setup() {
Serial.begin(115200);
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("\nWiFi connected");
}
void loop() {
float temp = 22.5; // Read from sensor
float humid = 65; // Read from sensor
sendData(temp, humid);
delay(60000); // Send every minute
}
Common Errors
401 Unauthorized
{
"error": "Unauthorized",
"message": "Invalid or missing API key"
}
Solutions:
- Check your API key is correct
- Verify the
X-API-Keyheader is included - Ensure the key hasn't been revoked
400 Validation Error
{
"error": "Validation Error",
"details": [
{
"path": ["body", "bucketId"],
"message": "Expected string, received undefined"
}
]
}
Solutions:
- Check all required fields are included
- Verify data types match the schema
- Ensure IDs are valid ObjectIds
404 Not Found
{
"error": "Not Found",
"message": "Bucket not found"
}
Solutions:
- Verify the
bucketIdis correct - Check the bucket belongs to your organization
- Ensure the bucket status is "active"
Best Practices
1. Batch Your Requests
Instead of:
# BAD: 100 individual requests
for i in {1..100}; do
curl -X POST https://api.dakkio.io/api/data -d "{...}"
done
Do this:
# GOOD: 1 batch request
curl -X POST https://api.dakkio.io/api/data/batch -d "{
\"dataPoints\": [ ... 100 points ... ]
}"
2. Handle Timestamps Properly
Always use UTC ISO 8601 format:
// ✅ GOOD
timestamp: new Date().toISOString() // "2024-01-15T10:30:00.123Z"
// ❌ BAD
timestamp: Date.now() // 1705318200123 (milliseconds)
timestamp: "15/01/2024" // Wrong format
3. Include Metadata
Add context to your data:
{
"values": {
"temperature": 22.5
},
"metadata": {
"deviceId": "ESP32-001",
"location": "Living Room",
"firmwareVersion": "1.2.3",
"batteryLevel": 85
}
}
4. Implement Retry Logic
async function sendDataWithRetry(data, maxRetries = 3) {
for (let i = 0; i < maxRetries; i++) {
try {
const response = await axios.post(url, data, config);
return response.data;
} catch (error) {
if (i === maxRetries - 1) throw error;
await new Promise(resolve => setTimeout(resolve, 1000 * (i + 1)));
}
}
}
Next Steps
Now that you've made your first request:
- Set Up Alerts - Get notified of important events
- Configure Webhooks - Integrate with external services
- Explore Data Queries - Learn advanced querying
- See More Examples - Real-world use cases