Skip to main content
GuidesAPI ReferenceExamples

Asset Location History

|

Retrieve and analyze historical GPS traces to understand asset movements, verify routes, and generate detailed analytics.

Overview

Location history provides tracking data over time, enabling route analysis, compliance verification, performance optimization, and incident investigation.

Use Case

Organizations tracking asset movements need to:

  • Verify completed routes match planned schedules
  • Analyze movement patterns for efficiency improvements
  • Calculate mileage for billing or expense reporting
  • Investigate incidents by reviewing historical paths
  • Optimize future planning based on real-world data

Example 1: Retrieve Location History

Fetch GPS trace data for a specific time window.

curl -X GET https://api.magiclane.net/api/v1/get_locations_of_asset_in_interval \
-H "Authorization: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-H "Accept: application/json" \
-d '{
"p_asset_id": "bike_301",
"p_start_time": 1766493579,
"p_end_time": 1766493607,
"p_page_no": 1,
"p_entries_per_page": 20
}'

Response Example (code 200 OK)

{
"locations_history": [
{
"speed": 6,
"bearing": 25,
"accuracy": 0.5,
"altitude": null,
"location": [25.608245938, 45.64818],
"timestamp": 1766493607
},
{
"speed": 6,
"bearing": 25,
"accuracy": 0.5,
"altitude": null,
"location": [25.60871, 45.647718125],
"timestamp": 1766493579
}
],
"page": {
"total_entries": 2,
"offset_entries": 0,
"total_pages": 1,
"page_no": 1,
"entries_per_page": 20,
"has_more": false
}
}

Example 2: Paginate Large Datasets

Retrieve complete history when data spans multiple pages.

class HistoryAggregator {
constructor(apiKey) {
this.apiKey = apiKey;
this.baseUrl = 'https://api.magiclane.net/api/v1';
}

async fetchCompleteHistory(assetId, startTime, endTime) {
const allPoints = [];
let currentPage = 1;
let moreDataAvailable = true;
const pointsPerPage = 1000;

while (moreDataAvailable) {
const response = await fetch(
`${this.baseUrl}/get_locations_of_asset_in_interval`,
{
method: 'GET',
headers: {
'Authorization': this.apiKey,
'Content-Type': 'application/json',
'Accept': 'application/json'
},
body: JSON.stringify({
p_asset_id: assetId,
p_start_time: startTime,
p_end_time: endTime,
p_page_no: currentPage,
p_entries_per_page: pointsPerPage
})
}
);

const pageData = await response.json();
const points = pageData.locations_history;

allPoints.push(...points);
console.log(`Page ${currentPage}: ${points.length} points fetched`);

moreDataAvailable = pageData.page.has_more;
currentPage++;
}

const totalHours = (endTime - startTime) / 3600;

return {
points: allPoints,
count: allPoints.length,
duration_hours: totalHours,
avg_points_per_hour: allPoints.length / totalHours
};
}
}

// Fetch week's worth of data
const aggregator = new HistoryAggregator('YOUR_API_KEY');
const weekAgoUnix = Math.floor(Date.now() / 1000) - (7 * 24 * 3600);
const nowUnix = Math.floor(Date.now() / 1000);

const weekData = await aggregator.fetchCompleteHistory(
'vehicle_101',
weekAgoUnix,
nowUnix
);

console.log(`Total GPS points: ${weekData.count}`);
console.log(`Average: ${weekData.avg_points_per_hour.toFixed(1)} points/hour`);

Example 3: Real-Time Location Monitoring

Monitor an asset's current position and movement in real-time using the latest location data.

class RealTimeLocationMonitor {
constructor(apiKey) {
this.apiKey = apiKey;
this.baseUrl = 'https://api.magiclane.net/api/v1';
this.monitoringAssets = new Map();
}

async getLastLocation(assetId) {
const response = await fetch(
`${this.baseUrl}/get_last_location_of_asset`,
{
method: 'GET',
headers: {
'Authorization': this.apiKey,
'Content-Type': 'application/json',
'Accept': 'application/json'
},
body: JSON.stringify({
p_asset_id: assetId
})
}
);

const data = await response.json();
return data.last_location_data;
}

async startMonitoring(assetId, updateIntervalMs = 5000, callback) {
console.log(`Starting real-time monitoring for ${assetId}...`);

const monitor = setInterval(async () => {
try {
const location = await this.getLastLocation(assetId);

const locationInfo = {
asset_id: assetId,
coordinates: location.last_location,
latitude: location.last_location[1],
longitude: location.last_location[0],
speed_mps: location.speed,
speed_kmh: (location.speed * 3.6).toFixed(1),
bearing: location.bearing,
accuracy: location.accuracy,
timestamp: location.timestamp,
time: new Date(location.timestamp * 1000).toLocaleString()
};

// Call custom callback
if (callback) {
callback(locationInfo);
} else {
// Default display
console.log(`[${locationInfo.time}] ${assetId}:`);
console.log(` Position: ${locationInfo.latitude}, ${locationInfo.longitude}`);
console.log(` Speed: ${locationInfo.speed_kmh} km/h`);
console.log(` Bearing: ${locationInfo.bearing}°`);
}
} catch (error) {
console.error(`Error monitoring ${assetId}:`, error.message);
}
}, updateIntervalMs);

this.monitoringAssets.set(assetId, monitor);
return monitor;
}

stopMonitoring(assetId) {
if (this.monitoringAssets.has(assetId)) {
clearInterval(this.monitoringAssets.get(assetId));
this.monitoringAssets.delete(assetId);
console.log(`Stopped monitoring ${assetId}`);
}
}

stopAll() {
this.monitoringAssets.forEach((monitor, assetId) => {
this.stopMonitoring(assetId);
});
}
}

// Usage example: Monitor a delivery vehicle in real-time
const monitor = new RealTimeLocationMonitor('YOUR_API_KEY');

// Start monitoring with custom callback
await monitor.startMonitoring('vehicle_101', 5000, (location) => {
// Custom handling - e.g., update map, check geofences, etc.
console.log(`Vehicle at: ${location.latitude}, ${location.longitude}`);
console.log(`Current speed: ${location.speed_kmh} km/h`);

// Example: Alert if speeding
if (parseFloat(location.speed_kmh) > 80) {
console.log('⚠️ ALERT: Vehicle exceeding speed limit!');
}

// Example: Update dashboard/map
// updateMapMarker(location.asset_id, location.coordinates);
});

// Monitor multiple assets simultaneously
await monitor.startMonitoring('truck_205', 10000);
await monitor.startMonitoring('bike_301', 3000);

// Stop monitoring specific asset
// monitor.stopMonitoring('vehicle_101');

// Stop all monitoring
// monitor.stopAll();

Example 4: Export to GeoJSON

Convert location history to GeoJSON format for use with mapping tools and visualization libraries.

function convertToGeoJSON(assetId, assetName, locationHistory) {
const coordinates = locationHistory.map(point => point.location);

return {
type: "FeatureCollection",
features: [
{
type: "Feature",
properties: {
asset_id: assetId,
asset_name: assetName,
point_count: coordinates.length,
start_time: locationHistory[0]?.timestamp,
end_time: locationHistory[locationHistory.length - 1]?.timestamp,
start_time_formatted: new Date(locationHistory[0]?.timestamp * 1000).toISOString(),
end_time_formatted: new Date(locationHistory[locationHistory.length - 1]?.timestamp * 1000).toISOString()
},
geometry: {
type: "LineString",
coordinates: coordinates
}
}
]
};
}

// Export route as GeoJSON
const histData = await fetchLocationHistory('vehicle_101', startTime, endTime);
const geoJson = convertToGeoJSON(
'vehicle_101',
'Delivery Van 101',
histData.locations_history
);

// Save to file or send to mapping service
console.log(JSON.stringify(geoJson, null, 2));