### Geofence Creation and Management with API Fetch
Source: https://context7.com/traccar/traccar-web/llms.txt
Demonstrates creating circular and polygon geofences using POST requests to the /api/geofences endpoint. It also shows how to link geofences to devices and retrieve geofence data. This snippet assumes a running Traccar server and valid authentication.
```javascript
// Create a circular geofence
const circleGeofence = {
name: 'Warehouse Zone',
description: 'Main warehouse perimeter',
area: 'CIRCLE (40.7128 -74.0060, 500)', // WKT format: lat lon, radius in meters
attributes: {
color: '#4CAF50',
speedLimit: 20
}
};
const createGeoResponse = await fetch('/api/geofences', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(circleGeofence)
});
const createdGeofence = await createGeoResponse.json();
// Create a polygon geofence
const polygonGeofence = {
name: 'Delivery Area',
area: 'POLYGON ((40.7128 -74.0060, 40.7138 -74.0050, 40.7148 -74.0070, 40.7128 -74.0060))',
attributes: {
color: '#2196F3'
}
};
await fetch('/api/geofences', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(polygonGeofence)
});
// Link geofence to device
await fetch('/api/permissions', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
deviceId: 123,
geofenceId: createdGeofence.id
})
});
// Get all geofences
const geofencesResponse = await fetch('/api/geofences');
const geofences = await geofencesResponse.json();
// Get geofences for specific device
const deviceGeoResponse = await fetch('/api/geofences?deviceId=123');
const deviceGeofences = await deviceGeoResponse.json();
// Listen for geofence events via WebSocket
socket.onmessage = (event) => {
const data = JSON.parse(event.data);
if (data.events) {
data.events.forEach(evt => {
if (evt.type === 'geofenceEnter') {
console.log(`Device ${evt.deviceId} entered geofence ${evt.geofenceId}`);
} else if (evt.type === 'geofenceExit') {
console.log(`Device ${evt.deviceId} exited geofence ${evt.geofenceId}`);
}
});
}
};
```
--------------------------------
### Real-Time Position Tracking with WebSockets and API Fetch
Source: https://context7.com/traccar/traccar-web/llms.txt
Establishes a WebSocket connection to receive live device position updates and device status changes. It also demonstrates fetching the latest positions and historical position data using the API. This snippet requires a running Traccar server and a compatible WebSocket client environment.
```javascript
// Establish WebSocket connection for real-time updates
const protocol = window.location.protocol === 'https:' ? 'wss:' : 'ws:';
const socket = new WebSocket(`${protocol}//${window.location.host}/api/socket`);
socket.onopen = () => {
console.log('WebSocket connected');
};
socket.onmessage = (event) => {
const data = JSON.parse(event.data);
// Handle position updates
if (data.positions) {
data.positions.forEach(position => {
console.log(`Device ${position.deviceId} at ${position.latitude}, ${position.longitude}`);
console.log(`Speed: ${position.speed} knots, Course: ${position.course}°`);
console.log(`Battery: ${position.attributes.batteryLevel}%`);
console.log(`Address: ${position.address}`);
});
}
// Handle device status changes
if (data.devices) {
data.devices.forEach(device => {
console.log(`Device ${device.id} status: ${device.status}`);
// status: 'online', 'offline', or 'unknown'
});
}
// Handle events (alarms, geofence triggers, etc.)
if (data.events) {
data.events.forEach(event => {
console.log(`Event: ${event.type} for device ${event.deviceId}`);
if (event.type === 'alarm') {
console.log(`Alarm type: ${event.attributes.alarm}`);
}
});
}
};
socket.onerror = (error) => {
console.error('WebSocket error:', error);
};
socket.onclose = () => {
console.log('WebSocket disconnected - reconnecting in 60s');
setTimeout(() => location.reload(), 60000);
};
// Get latest positions for all devices
const positionsResponse = await fetch('/api/positions');
const positions = await positionsResponse.json();
// Get position history for a device
const from = new Date('2025-01-01T00:00:00Z').toISOString();
const to = new Date('2025-01-01T23:59:59Z').toISOString();
const historyResponse = await fetch(
`/api/positions?deviceId=123&from=${from}&to=${to}`
);
const history = await historyResponse.json();
console.log(`Retrieved ${history.length} historical positions`);
```
--------------------------------
### Initialize and Render Map with Device Markers using MapLibre GL JS (React)
Source: https://context7.com/traccar/traccar-web/llms.txt
This JavaScript code snippet initializes a MapLibre GL map within a React component. It sets up the map container, style, center, and zoom level. It also configures sources and layers for displaying device markers, including clustering for a large number of devices. Dependencies include MapLibre GL JS and React hooks.
```javascript
import maplibregl from 'maplibre-gl';
import { useEffect, useRef } from 'react';
import { useSelector } from 'react-redux';
// Initialize map
const MapComponent = () => {
const mapContainer = useRef(null);
const map = useRef(null);
const devices = useSelector((state) => state.devices.items);
const positions = useSelector((state) => state.session.positions);
useEffect(() => {
if (map.current) return; // Initialize only once
map.current = new maplibregl.Map({
container: mapContainer.current,
style: 'https://tiles.locationiq.com/v3/streets/vector.json?key=YOUR_KEY',
center: [-74.0060, 40.7128], // [lng, lat]
zoom: 12
});
// Add navigation controls
map.current.addControl(new maplibregl.NavigationControl());
// Wait for map to load
map.current.on('load', () => {
// Add device markers source
map.current.addSource('devices', {
type: 'geojson',
data: {
type: 'FeatureCollection',
features: []
}
});
// Add device markers layer
map.current.addLayer({
id: 'device-markers',
type: 'symbol',
source: 'devices',
layout: {
'icon-image': ['get', 'category'], // Use category for icon
'icon-size': 0.5,
'icon-rotate': ['get', 'rotation'],
'icon-rotation-alignment': 'map',
'icon-allow-overlap': true
}
});
// Add device clustering
map.current.addSource('device-clusters', {
type: 'geojson',
data: { type: 'FeatureCollection', features: [] },
cluster: true,
clusterMaxZoom: 14,
clusterRadius: 50
});
map.current.addLayer({
id: 'clusters',
type: 'circle',
source: 'device-clusters',
filter: ['has', 'point_count'],
paint: {
'circle-color': '#2196F3',
'circle-radius': 20
}
});
map.current.addLayer({
id: 'cluster-count',
type: 'symbol',
source: 'device-clusters',
filter: ['has', 'point_count'],
layout: {
'text-field': '{point_count_abbreviated}',
'text-size': 12
},
paint: {
'text-color': '#FFFFFF'
}
});
});
}, []);
// Update device positions
useEffect(() => {
if (!map.current || !map.current.loaded()) return;
const features = Object.values(devices).map((device) => {
const position = positions[device.id];
if (!position) return null;
return {
type: 'Feature',
geometry: {
type: 'Point',
coordinates: [position.longitude, position.latitude]
},
properties: {
id: device.id,
name: device.name,
category: device.category || 'default',
status: device.status,
rotation: position.course || 0
}
};
}).filter(Boolean);
const source = map.current.getSource('devices');
if (source) {
source.setData({
type: 'FeatureCollection',
features
});
}
}, [devices, positions]);
// Add click handler for device markers
useEffect(() => {
if (!map.current) return;
const handleClick = (e) => {
const feature = e.features[0];
const deviceId = feature.properties.id;
// Show popup
new maplibregl.Popup()
.setLngLat(e.lngLat)
.setHTML(
`
${feature.properties.name}
Status: ${feature.properties.status}
`
)
.addTo(map.current);
};
map.current.on('click', 'device-markers', handleClick);
return () => {
map.current.off('click', 'device-markers', handleClick);
};
}, []);
return ;
};
export default MapComponent;
```
--------------------------------
### Manage Drivers and QR Code Integration (JavaScript)
Source: https://context7.com/traccar/traccar-web/llms.txt
This JavaScript snippet outlines the process of managing drivers within Traccar, including creating driver profiles, linking them to devices, and generating QR codes for identification. It also shows how to handle driver identification when a device scans a QR code. This code is intended for a browser environment and relies on the Traccar API and a QR code generation library.
```javascript
// Create driver
const driver = {
name: 'John Smith',
uniqueId: 'DRV-1234',
attributes: {
phone: '+1234567890',
licenseNumber: 'DL123456789',
licenseExpiry: '2027-12-31'
}
};
const driverResponse = await fetch('/api/drivers', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(driver)
});
const createdDriver = await driverResponse.json();
// Link driver to device
await fetch('/api/permissions', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
deviceId: 123,
driverId: createdDriver.id
})
});
// Get drivers for device
const deviceDriversResponse = await fetch('/api/drivers?deviceId=123');
const deviceDrivers = await deviceDriversResponse.json();
// Generate QR code for driver (browser-side)
import QRCode from 'react-qr-code';
const DriverQRCode = ({ driver }) => {
// QR code data format expected by Traccar devices
const qrData = JSON.stringify({
type: 'driver',
uniqueId: driver.uniqueId
});
return (
{driver.name}
Driver ID: {driver.uniqueId}
);
};
// Handle driver identification from device
// When device scans QR code, it sends driverUniqueId in position attributes
socket.onmessage = (event) => {
const data = JSON.parse(event.data);
if (data.positions) {
data.positions.forEach((position) => {
if (position.attributes.driverUniqueId) {
console.log(`Driver ${position.attributes.driverUniqueId} identified on device ${position.deviceId}`);
// Log trip with driver association
}
});
}
};
```
--------------------------------
### React Login and Registration Component
Source: https://github.com/traccar/traccar-web/blob/master/simple/index.html
Handles user login and new user registration. It makes POST requests to '/api/users' for registration and '/api/session' for login. It manages email and password input states and displays 'Register' or 'Login' button based on the server state.
```javascript
const LoginScreen = ({ server, setServer, setUser }) => {
const [email, setEmail] = React.useState('');
const [password, setPassword] = React.useState('');
const handleSubmit = (event) => {
event.preventDefault();
const fetchData = async () => {
if (server.newServer) {
const response = await fetch('/api/users', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({ name: email, email, password }),
});
if (response.ok) {
setServer({ ...server, newServer: false });
}
} else {
const query = `email=${encodeURIComponent(email)}&password=${encodeURIComponent(password)}`;
const response = await fetch('/api/session', {
method: 'POST',
body: new URLSearchParams(query),
});
if (response.ok) {
setUser(await response.json());
}
}
};
fetchData();
};
const formStyle = {
width: '320px',
margin: '32px',
display: 'flex',
flexDirection: 'column',
};
return (
);
};
```
--------------------------------
### Manage Traccar Users, Groups, and Permissions with JavaScript API
Source: https://context7.com/traccar/traccar-web/llms.txt
This snippet demonstrates how to use the Traccar API with JavaScript to create and manage users, establish hierarchical device groups, link devices to groups, and manage user permissions. It covers user creation, preference updates, device-to-user linking, group creation (root and sub-groups), device-to-group assignment, and retrieving user groups.
```javascript
// Create new user
const newUser = {
name: 'Fleet Manager',
email: 'manager@example.com',
password: 'SecurePass123!',
phone: '+1234567890',
readonly: false,
administrator: false,
deviceLimit: 100,
userLimit: 10,
expirationTime: '2026-12-31T23:59:59Z',
attributes: {
timezone: 'America/New_York',
speedUnit: 'kmh',
distanceUnit: 'km',
volumeUnit: 'liter'
}
};
const userResponse = await fetch('/api/users', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(newUser)
});
const createdUser = await userResponse.json();
// Update user preferences
await fetch(`/api/users/${createdUser.id}`, {
method: 'PUT',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
...createdUser,
attributes: {
...createdUser.attributes,
mapDefault: 'locationIqStreets',
darkMode: true
}
})
});
// Link device to user
await fetch('/api/permissions', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
userId: createdUser.id,
deviceId: 123
})
});
// Create hierarchical device group
const rootGroup = {
name: 'North America Fleet',
attributes: {
speedLimit: 110,
fuelPrice: 1.5
}
};
const rootResponse = await fetch('/api/groups', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(rootGroup)
});
const root = await rootResponse.json();
// Create sub-group
const subGroup = {
name: 'Eastern Region',
groupId: root.id, // Parent group
attributes: {
timezone: 'America/New_York'
}
};
const subResponse = await fetch('/api/groups', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(subGroup)
});
const sub = await subResponse.json();
// Assign device to group
await fetch(`/api/devices/123`, {
method: 'PUT',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
id: 123,
groupId: sub.id,
// ... other device properties
})
});
// Link group to user
await fetch('/api/permissions', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
userId: createdUser.id,
groupId: root.id
})
});
// Get all groups for user
const userGroupsResponse = await fetch(`/api/groups?userId=${createdUser.id}`);
const userGroups = await userGroupsResponse.json();
```
--------------------------------
### User and Group Management API
Source: https://context7.com/traccar/traccar-web/llms.txt
Endpoints for managing users, roles, and hierarchical device groups. This includes creating, updating, linking users to devices and groups, and managing group structures.
```APIDOC
## POST /api/users
### Description
Creates a new user in the system.
### Method
POST
### Endpoint
/api/users
### Parameters
#### Request Body
- **name** (string) - Required - The name of the user.
- **email** (string) - Required - The email address of the user.
- **password** (string) - Required - The password for the user.
- **phone** (string) - Optional - The phone number of the user.
- **readonly** (boolean) - Optional - Whether the user is read-only.
- **administrator** (boolean) - Optional - Whether the user is an administrator.
- **deviceLimit** (integer) - Optional - The maximum number of devices the user can manage.
- **userLimit** (integer) - Optional - The maximum number of users the user can create.
- **expirationTime** (string) - Optional - The expiration date and time for the user account in ISO 8601 format.
- **attributes** (object) - Optional - A key-value map of user attributes.
- **timezone** (string) - Optional - The user's timezone.
- **speedUnit** (string) - Optional - The preferred unit for speed.
- **distanceUnit** (string) - Optional - The preferred unit for distance.
- **volumeUnit** (string) - Optional - The preferred unit for volume.
### Request Example
{
"name": "Fleet Manager",
"email": "manager@example.com",
"password": "SecurePass123!",
"phone": "+1234567890",
"readonly": false,
"administrator": false,
"deviceLimit": 100,
"userLimit": 10,
"expirationTime": "2026-12-31T23:59:59Z",
"attributes": {
"timezone": "America/New_York",
"speedUnit": "kmh",
"distanceUnit": "km",
"volumeUnit": "liter"
}
}
### Response
#### Success Response (200)
- **id** (integer) - The unique identifier of the created user.
- **name** (string) - The name of the user.
- **email** (string) - The email address of the user.
- **phone** (string) - The phone number of the user.
- **readonly** (boolean) - Whether the user is read-only.
- **administrator** (boolean) - Whether the user is an administrator.
- **deviceLimit** (integer) - The maximum number of devices the user can manage.
- **userLimit** (integer) - The maximum number of users the user can create.
- **expirationTime** (string) - The expiration date and time for the user account.
- **attributes** (object) - A key-value map of user attributes.
#### Response Example
{
"id": 1,
"name": "Fleet Manager",
"email": "manager@example.com",
"phone": "+1234567890",
"readonly": false,
"administrator": false,
"deviceLimit": 100,
"userLimit": 10,
"expirationTime": "2026-12-31T23:59:59Z",
"attributes": {
"timezone": "America/New_York",
"speedUnit": "kmh",
"distanceUnit": "km",
"volumeUnit": "liter"
}
}
## PUT /api/users/{id}
### Description
Updates an existing user's information and preferences.
### Method
PUT
### Endpoint
/api/users/{id}
### Parameters
#### Path Parameters
- **id** (integer) - Required - The unique identifier of the user to update.
#### Request Body
- **id** (integer) - Required - The unique identifier of the user.
- **name** (string) - Optional - The updated name of the user.
- **email** (string) - Optional - The updated email address of the user.
- **password** (string) - Optional - The updated password for the user.
- **phone** (string) - Optional - The updated phone number of the user.
- **readonly** (boolean) - Optional - The updated read-only status.
- **administrator** (boolean) - Optional - The updated administrator status.
- **deviceLimit** (integer) - Optional - The updated device limit.
- **userLimit** (integer) - Optional - The updated user limit.
- **expirationTime** (string) - Optional - The updated expiration date and time.
- **attributes** (object) - Optional - The updated user attributes.
- **mapDefault** (string) - Optional - The default map layer.
- **darkMode** (boolean) - Optional - Whether dark mode is enabled.
### Request Example
{
"id": 1,
"name": "Fleet Manager",
"email": "manager@example.com",
"password": "SecurePass123!",
"phone": "+1234567890",
"readonly": false,
"administrator": false,
"deviceLimit": 100,
"userLimit": 10,
"expirationTime": "2026-12-31T23:59:59Z",
"attributes": {
"timezone": "America/New_York",
"speedUnit": "kmh",
"distanceUnit": "km",
"volumeUnit": "liter",
"mapDefault": "locationIqStreets",
"darkMode": true
}
}
### Response
#### Success Response (200)
Returns the updated user object.
#### Response Example
{
"id": 1,
"name": "Fleet Manager",
"email": "manager@example.com",
"phone": "+1234567890",
"readonly": false,
"administrator": false,
"deviceLimit": 100,
"userLimit": 10,
"expirationTime": "2026-12-31T23:59:59Z",
"attributes": {
"timezone": "America/New_York",
"speedUnit": "kmh",
"distanceUnit": "km",
"volumeUnit": "liter",
"mapDefault": "locationIqStreets",
"darkMode": true
}
}
## POST /api/permissions
### Description
Creates a permission link between a user and a device or a user and a group.
### Method
POST
### Endpoint
/api/permissions
### Parameters
#### Request Body
- **userId** (integer) - Required - The ID of the user.
- **deviceId** (integer) - Optional - The ID of the device to link.
- **groupId** (integer) - Optional - The ID of the group to link.
### Request Example
{
"userId": 1,
"deviceId": 123
}
### Response
#### Success Response (200)
Indicates that the permission was successfully created.
### Response Example
(No specific response body provided, typically an empty 200 OK or a success message)
## POST /api/groups
### Description
Creates a new device group, which can be a root group or a sub-group.
### Method
POST
### Endpoint
/api/groups
### Parameters
#### Request Body
- **name** (string) - Required - The name of the group.
- **groupId** (integer) - Optional - The ID of the parent group if creating a sub-group.
- **attributes** (object) - Optional - A key-value map of group attributes.
- **speedLimit** (integer) - Optional - The speed limit for the group.
- **fuelPrice** (number) - Optional - The fuel price for the group.
- **timezone** (string) - Optional - The timezone for the group.
### Request Example
{
"name": "North America Fleet",
"attributes": {
"speedLimit": 110,
"fuelPrice": 1.5
}
}
### Response
#### Success Response (200)
- **id** (integer) - The unique identifier of the created group.
- **name** (string) - The name of the group.
- **groupId** (integer) - The ID of the parent group, if applicable.
- **attributes** (object) - A key-value map of group attributes.
#### Response Example
{
"id": 1,
"name": "North America Fleet",
"groupId": null,
"attributes": {
"speedLimit": 110,
"fuelPrice": 1.5
}
}
## PUT /api/devices/{id}
### Description
Updates an existing device's properties, including its group assignment.
### Method
PUT
### Endpoint
/api/devices/{id}
### Parameters
#### Path Parameters
- **id** (integer) - Required - The unique identifier of the device to update.
#### Request Body
- **id** (integer) - Required - The unique identifier of the device.
- **groupId** (integer) - Optional - The ID of the group to assign the device to.
- ... other device properties can be included here
### Request Example
{
"id": 123,
"groupId": 2
}
### Response
#### Success Response (200)
Indicates that the device was successfully updated.
### Response Example
(No specific response body provided, typically an empty 200 OK or a success message)
## GET /api/groups?userId={userId}
### Description
Retrieves all groups associated with a specific user.
### Method
GET
### Endpoint
/api/groups?userId={userId}
### Parameters
#### Query Parameters
- **userId** (integer) - Required - The ID of the user whose groups are to be retrieved.
### Response
#### Success Response (200)
- An array of group objects associated with the user.
#### Response Example
[
{
"id": 1,
"name": "North America Fleet",
"groupId": null,
"attributes": {
"speedLimit": 110,
"fuelPrice": 1.5
}
},
{
"id": 2,
"name": "Eastern Region",
"groupId": 1,
"attributes": {
"timezone": "America/New_York"
}
}
]
```
--------------------------------
### Commands API
Source: https://context7.com/traccar/traccar-web/llms.txt
This API allows for retrieving command types, sending commands to devices, and managing saved commands.
```APIDOC
## GET /api/commands/types
### Description
Retrieves a list of available command types that can be sent to a specific device.
### Method
GET
### Endpoint
/api/commands/types
### Parameters
#### Query Parameters
- **deviceId** (integer) - Required - The ID of the device for which to get command types.
### Response
#### Success Response (200)
An array of strings, where each string is a command type identifier.
#### Response Example
```json
["positionPeriodic", "engineStop", "engineResume", "outputControl", "custom"]
```
## POST /api/commands/send
### Description
Sends a command to a specified device.
### Method
POST
### Endpoint
/api/commands/send
### Parameters
#### Request Body
- **deviceId** (integer) - Required - The ID of the target device.
- **type** (string) - Required - The type of command to send (e.g., 'positionPeriodic', 'engineStop').
- **attributes** (object) - Optional - Additional attributes for the command (e.g., {"frequency": 30}).
### Request Example
```json
{
"deviceId": 123,
"type": "positionPeriodic",
"attributes": {
"frequency": 30
}
}
```
### Response
#### Success Response (200)
Indicates the command was sent successfully.
#### Error Response (4xx/5xx)
Details about the failure to send the command.
## POST /api/commands
### Description
Saves a command as a template for future use.
### Method
POST
### Endpoint
/api/commands
### Parameters
#### Request Body
- **description** (string) - Optional - A description for the saved command.
- **type** (string) - Required - The type of command.
- **attributes** (object) - Required - The attributes associated with the command.
### Request Example
```json
{
"description": "Request Position Every 30s",
"type": "positionPeriodic",
"attributes": {
"frequency": 30
}
}
```
### Response
#### Success Response (200)
Returns the saved command object, including its assigned ID.
#### Response Example
```json
{
"id": 5,
"description": "Request Position Every 30s",
"type": "positionPeriodic",
"attributes": {
"frequency": 30
}
}
```
## POST /api/permissions
### Description
Links a saved command to a specific device, allowing the device to use the command template.
### Method
POST
### Endpoint
/api/permissions
### Parameters
#### Request Body
- **deviceId** (integer) - Required - The ID of the device.
- **commandId** (integer) - Required - The ID of the saved command.
### Request Example
```json
{
"deviceId": 123,
"commandId": 5
}
```
### Response
#### Success Response (200)
Indicates the permission was granted successfully.
## GET /api/commands
### Description
Retrieves a list of saved commands associated with a specific device.
### Method
GET
### Endpoint
/api/commands
### Parameters
#### Query Parameters
- **deviceId** (integer) - Optional - The ID of the device to filter commands by.
### Response
#### Success Response (200)
An array of saved command objects.
#### Response Example
```json
[
{
"id": 5,
"description": "Request Position Every 30s",
"type": "positionPeriodic",
"attributes": {
"frequency": 30
}
}
]
```
```
--------------------------------
### Redux State Management with Redux Toolkit (JavaScript)
Source: https://context7.com/traccar/traccar-web/llms.txt
Manages application state for devices, positions, and user session using Redux Toolkit. This includes defining reducers, configuring the store, and providing hooks for component interaction. It handles data fetching, WebSocket updates, and state selection.
```javascript
import { configureStore, createSlice } from '@reduxjs/toolkit';
import { useSelector, useDispatch } from 'react-redux';
// Device slice
const devicesSlice = createSlice({
name: 'devices',
initialState: {
items: {},
selectedId: null,
selectTime: null
},
reducers: {
refresh: (state, action) => {
state.items = {};
action.payload.forEach((device) => {
state.items[device.id] = device;
});
},
update: (state, action) => {
action.payload.forEach((device) => {
state.items[device.id] = device;
});
},
selectId: (state, action) => {
state.selectedId = action.payload;
state.selectTime = Date.now();
},
remove: (state, action) => {
delete state.items[action.payload];
if (state.selectedId === action.payload) {
state.selectedId = null;
}
}
}
});
// Session slice
const sessionSlice = createSlice({
name: 'session',
initialState: {
server: null,
user: null,
socket: false,
positions: {},
history: {}
},
reducers: {
updateServer: (state, action) => {
state.server = action.payload;
},
updateUser: (state, action) => {
state.user = action.payload;
},
updateSocket: (state, action) => {
state.socket = action.payload;
},
updatePositions: (state, action) => {
action.payload.forEach((position) => {
state.positions[position.deviceId] = position;
});
}
}
});
// Configure store
const store = configureStore({
reducer: {
devices: devicesSlice.reducer,
session: sessionSlice.reducer
}
});
// Export actions
export const { refresh, update, selectId, remove } = devicesSlice.actions;
export const { updateServer, updateUser, updateSocket, updatePositions } = sessionSlice.actions;
// Usage in components
const DeviceList = () => {
const dispatch = useDispatch();
const devices = useSelector((state) => Object.values(state.devices.items));
const selectedId = useSelector((state) => state.devices.selectedId);
const positions = useSelector((state) => state.session.positions);
// Load devices on mount
useEffect(() => {
const loadDevices = async () => {
const response = await fetch('/api/devices');
const data = await response.json();
dispatch(refresh(data));
};
loadDevices();
}, [dispatch]);
// Handle WebSocket updates
useEffect(() => {
const socket = new WebSocket('ws://localhost:8082/api/socket');
socket.onmessage = (event) => {
const data = JSON.parse(event.data);
if (data.devices) {
dispatch(update(data.devices));
}
if (data.positions) {
dispatch(updatePositions(data.positions));
}
};
return () => socket.close();
}, [dispatch]);
return (
{devices.map((device) => {
const position = positions[device.id];
return (
dispatch(selectId(device.id))}
style={{
background: device.id === selectedId ? '#E3F2FD' : 'transparent'
}}
>
{device.name}
Status: {device.status}
{position && (
Speed: {(position.speed * 1.852).toFixed(1)} km/h
)}
);
})}
);
};
export default store;
```
--------------------------------
### React Application Root Component
Source: https://github.com/traccar/traccar-web/blob/master/simple/index.html
The main App component orchestrates the application's state management for server configuration and user authentication. It fetches initial server and session data on mount. It conditionally renders either the MainScreen or LoginScreen based on user authentication status.
```javascript
const App = () => {
const [server, setServer] = React.useState();
const [user, setUser] = React.useState();
React.useEffect(() => {
const fetchData = async () => {
const serverResponse = await fetch('/api/server');
if (serverResponse.ok) {
setServer(await serverResponse.json());
}
const sessionResponse = await fetch('/api/session');
if (sessionResponse.ok) {
setUser(await sessionResponse.json());
}
}
fetchData();
}, []);
return user ? (
) : server ? (
) : '';
};
ReactDOM.render(, document.getElementById('content'));
```
--------------------------------
### Configure Event Notifications via API (JavaScript)
Source: https://context7.com/traccar/traccar-web/llms.txt
This JavaScript code snippet demonstrates how to interact with the Traccar Web API to configure event-based notifications. It shows how to retrieve available event types and notification channels, create new notifications, link them to devices, test them, and send announcements. It utilizes `fetch` for API calls and assumes a JSON response structure.
```javascript
await fetch('/api/notifications/types');
const eventTypes = await eventTypesResponse.json();
console.log('Event types:', eventTypes);
await fetch('/api/notifications/notificators');
const notificators = await notificators.json();
console.log('Notification channels:', notificators);
const notification = {
type: 'deviceOverspeed',
always: false,
notificators: 'web,mail,firebase',
attributes: {
alarmEnabled: true
}
};
const notifResponse = await fetch('/api/notifications', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(notification)
});
const createdNotification = await notifResponse.json();
await fetch('/api/permissions', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
deviceId: 123,
notificationId: createdNotification.id
})
});
const geofenceNotification = {
type: 'geofenceEnter',
always: true,
notificators: 'telegram,mail',
attributes: {}
};
await fetch('/api/notifications', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(geofenceNotification)
});
const testResponse = await fetch('/api/notifications/test/mail', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
body: 'Test notification message'
})
});
if (testResponse.ok) {
console.log('Test notification sent successfully');
}
await fetch('/api/notifications/send/web', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
subject: 'System Maintenance',
body: 'Scheduled maintenance on Jan 15, 2025 from 2-4 AM'
})
});
```
--------------------------------
### Notification Configuration API
Source: https://context7.com/traccar/traccar-web/llms.txt
Endpoints for managing notification types, channels, and configurations.
```APIDOC
## GET /api/notifications/types
### Description
Retrieves a list of available event types for which notifications can be configured.
### Method
GET
### Endpoint
/api/notifications/types
### Parameters
None
### Request Example
None
### Response
#### Success Response (200)
- **eventTypes** (array) - A list of available notification event types.
#### Response Example
```json
[
"alarm",
"ignitionOn",
"ignitionOff",
"geofenceEnter",
"geofenceExit",
"deviceMoving",
"deviceStopped",
"deviceOverspeed",
"deviceFuelDrop"
]
```
## GET /api/notifications/notificators
### Description
Retrieves a list of available notification delivery channels.
### Method
GET
### Endpoint
/api/notifications/notificators
### Parameters
None
### Request Example
None
### Response
#### Success Response (200)
- **notificators** (array) - A list of available notification channels.
#### Response Example
```json
[
"web",
"mail",
"sms",
"firebase",
"telegram",
"traccar",
"command"
]
```
## POST /api/notifications
### Description
Creates a new notification configuration.
### Method
POST
### Endpoint
/api/notifications
### Parameters
#### Request Body
- **type** (string) - Required - The type of the event for the notification (e.g., 'deviceOverspeed', 'geofenceEnter').
- **always** (boolean) - Required - Specifies if the notification should be sent every time the event occurs.
- **notificators** (string) - Required - A comma-separated string of notification channels to use.
- **attributes** (object) - Optional - Additional attributes specific to the notification type.
### Request Example
```json
{
"type": "deviceOverspeed",
"always": false,
"notificators": "web,mail,firebase",
"attributes": {
"alarmEnabled": true
}
}
```
### Response
#### Success Response (200)
- **id** (integer) - The ID of the created notification.
#### Response Example
```json
{
"id": 1
}
```
## POST /api/permissions
### Description
Links a notification to a specific device.
### Method
POST
### Endpoint
/api/permissions
### Parameters
#### Request Body
- **deviceId** (integer) - Required - The ID of the device to link the notification to.
- **notificationId** (integer) - Required - The ID of the notification to link.
### Request Example
```json
{
"deviceId": 123,
"notificationId": 1
}
```
### Response
(No specific success response body detailed, assume 200 OK on success)
## POST /api/notifications/test/{notificator}
### Description
Tests sending a notification through a specific channel without saving the configuration.
### Method
POST
### Endpoint
/api/notifications/test/{notificator}
- **notificator** (string) - Path Parameter - The notification channel to test (e.g., 'mail').
### Parameters
#### Request Body
- **body** (string) - Required - The content of the test notification message.
### Request Example
```json
{
"body": "Test notification message"
}
```
### Response
#### Success Response (200)
Indicates the test notification was sent successfully.
#### Response Example
(No specific response body detailed, check for 200 OK status)
## POST /api/notifications/send/{notificator}
### Description
Sends an announcement to all users via a specified notification channel.
### Method
POST
### Endpoint
/api/notifications/send/{notificator}
- **notificator** (string) - Path Parameter - The notification channel to use for sending the announcement (e.g., 'web').
### Parameters
#### Request Body
- **subject** (string) - Required - The subject of the announcement.
- **body** (string) - Required - The main content of the announcement.
### Request Example
```json
{
"subject": "System Maintenance",
"body": "Scheduled maintenance on Jan 15, 2025 from 2-4 AM"
}
```
### Response
(No specific success response body detailed, assume 200 OK on success)
```
--------------------------------
### Session Authentication API - Traccar Web
Source: https://context7.com/traccar/traccar-web/llms.txt
Provides functions to log in, retrieve the current session, and log out of the Traccar platform. Uses the fetch API for HTTP requests. Handles authentication credentials and session management.
```javascript
const response = await fetch('/api/session', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
email: 'user@example.com',
password: 'securepassword123',
token: '123456' // Optional: TOTP 2FA code
})
});
if (response.ok) {
const user = await response.json();
console.log('Logged in:', user);
}
// Get current session
const sessionResponse = await fetch('/api/session');
if (sessionResponse.ok) {
const currentUser = await sessionResponse.json();
} else {
// Not authenticated - redirect to login
window.location.href = '/login';
}
// Logout
await fetch('/api/session', { method: 'DELETE' });
```