---
title: "Wialon Drivers API: Bind Drivers to Units | Asset Track"
url: https://theassettrack.com/wialon-api/drivers/
description: "Create drivers, bind them to units, read binding history over the Wialon Remote API — including the avl_driver auto-binding sensor."
---

# Wialon Drivers API: Bind Drivers to Units

Reference · last checked September 11, 2026

Create drivers, bind them to units, read binding history over the Wialon Remote API — including the avl_driver auto-binding sensor.

Driver assignment is where fleet reports meet payroll: the unit drove, but a person is paid. Wialon keeps the two halves in different places — units live under accounts, drivers live on resources — and joins them with explicit bindings. This page covers the full loop over the Remote API: creating a driver, binding it to a unit, reading the binding history back, and the automatic binding that skips the manual step entirely.

If the request format itself is new to you, read the [Postman setup](https://theassettrack.com/wialon-api/postman/) first — everything below is POST against `wialon/ajax.html` with `svc` and `params`, authenticated with a session id.

## Create the driver on a resource

Drivers belong to a resource, and creating one is `resource/update_driver` with `id` 0 and `callMode` “create”:

`https://hst-api.wialon.com/wialon/ajax.html?sid=<sid>&svc=resource/update_driver&params={"itemId":<resourceId>,"id":0,"callMode":"create","n":"A. Kazlou","c":"1042"}`

The short fields are the whole record: `n` is the name, `c` is the code, plus optional description (`ds`) and phone (`p`). The `c` code is the field hardware bindings match against later: iButton keys, RFID cards and tachograph driver cards all arrive as codes. Keep it unique per resource and treat it as the driver’s stable identifier — names change, codes should not. The same call with `callMode` “update” or “delete” and a real `id` edits or removes the driver.

## Send only the fields the call mode expects

One service covers create, update, delete and image reset, and the parameter set is the same for all four:

| Name | Meaning |
| --- | --- |
| `itemId` | Resource id — the driver’s parent, not the unit |
| `id` | Driver id; `0` creates |
| `callMode` | `create`, `update`, `delete` or `reset_image` |
| `n` | Name |
| `c` | Code — what hardware bindings match on |
| `ds` | Description |
| `p` | Phone, as `+1234567890`; the `+` must be encoded as `%2B` |
| `f` | Flags; `4` marks the driver exclusive |
| `pwd` | Password for mobile authorization |
| `jp` | Custom fields, as `"name":"value"` pairs |
| `ck`, `r`, `ej` | Image checksum, image aspect ratio, extended JSON |

Two of these cause more trouble than their size suggests. The phone encoding is a genuine trap: an unencoded `+` in a form-encoded body arrives as a space, and the driver ends up with a phone number that is silently wrong rather than rejected. And `f` with value `4` makes the driver exclusive, which changes what happens when a second binding arrives — set it deliberately rather than copying it out of an example.

On create and update the call returns the driver id together with the full record; on delete it returns the id and a null. Read the returned record rather than assuming your input was stored verbatim, because the server normalises some fields.

## Bind the driver to a unit

Manual binding is `resource/bind_unit_driver`, with an explicit mode — 1 binds, 0 unbinds:

`https://hst-api.wialon.com/wialon/ajax.html?sid=<sid>&svc=resource/bind_unit_driver&params={"resourceId":<resourceId>,"unitId":<unitId>,"driverId":<driverId>,"time":0,"mode":1}`

`time` 0 means now; a past timestamp backdates the binding. Success returns an empty object. Binding is a state change, not a record: one unit has one active driver at a time, and binding a second driver replaces the first. Two consequences follow. First, reports that group by driver (`report/get_report_data` with a driver grouping) attribute every event to whoever was bound at the event’s time — so a late manual binding rewrites the past as far as the report is concerned. Second, nothing in the API stops you from binding a driver to two units at once; the nonsense is yours to prevent.

Note that the call names both parents — `resourceId` and `unitId` — because it touches two objects in two different hierarchies. That is also why its rights requirements are the union of both, which is the subject of the errors section below.

## Let the hardware bind instead

Manual binding does not scale past a dozen vehicles. The production answer is a sensor of the “Driver assignment” type: a digital input (iButton reader, RFID, tachograph card slot) whose value is the driver’s code. When a message arrives with a code, Wialon binds the matching driver automatically and unbinds on the next code. Your integration then does nothing at bind time — it only reads.

This is why the `c` code field matters more than the name, and why the match is exact: the documentation calls out case explicitly — if the message carries `avl_driver=000a777e10`, the code field must read `000a777e10`, after any conversion applied to the parameter. A mistyped code means the hardware “binds” nobody, and the unit’s trips pile up under “no driver” while the dashboard looks fine. When driver-grouped reports show gaps, check code equality first: trailing spaces and leading zeros are the classic cause.

Two failure modes are worth building alerts for rather than discovering at month end. A reader that stops working produces a unit whose trips are all unassigned from a given date — visible as a cliff in any driver-grouped report. And a driver key that has been copied or shared produces a driver bound to two units simultaneously, which the API permits and the payroll department will not.

## List the drivers you already have

Drivers come back as part of the resource, not as a searchable catalogue of their own. Search resources with `core/search_items` and ask for the driver block in the data flags:

`svc=core/search_items&params={"spec":{"itemsType":"avl_resource","propName":"sys_name","propValueMask":"*","sortType":"sys_name"},"force":1,"flags":256,"from":0,"to":0}`

| Flag | Dec | Returns |
| --- | --- | --- |
| `0x00000100` | 256 | Drivers |
| `0x00008000` | 32768 | Driver groups |
| `0x00000400` | 1024 | Notifications |
| `0x00002000` | 8192 | Report templates |

Combine the bits you need in one call rather than making several: the flags are additive, and asking for drivers and driver groups together costs one request. As everywhere in this API, JSON carries the decimal form, so `0x100` goes into the request as `256`.

Driver groups are worth knowing about even if you do not use them yet. They are the natural place for shift teams, subcontractors and depots, and a report grouped by driver group answers a management question that a report grouped by driver does not.

## Read the binding state back

The driver object itself carries the binding: `bu` is the currently bound unit, `pu` the previously bound one, `bt` the time of the last binding change. To answer “who drove unit X on Tuesday”, read the drivers with their `bu`/`bt` fields and intersect with the unit’s trips for the interval.

That trio is a snapshot, not a history. It tells you the current binding and the one before it, with a timestamp — which is enough for live views and not enough for payroll. If you need the full sequence over a month, the binding changes have to be captured as they happen and stored on your side; a report grouped by driver is the alternative, and it answers the question for a chosen interval without giving you the underlying series.

One subtlety: a unit with no binding in an interval is not an error — it is a real state (yard moves, workshop visits, theft). Export code should emit an explicit “unassigned” row rather than dropping those trips, or the totals will not reconcile with the unit’s own mileage.

## The errors you will meet

- **Error 4 (invalid input)** on `update_driver` almost always means the resource id is wrong or the session’s access flags do not include driver management. The [token page](https://theassettrack.com/wialon-api/token/) has the flag table.
- **Error 7 (no rights)** on binding means the token can see the unit but not the resource, or vice versa. Binding touches both objects, so it needs rights on both.
- **Error 1002** on create means a driver with that code already exists on the resource. Treat it as a signal to update rather than to retry — a retry loop here creates nothing and looks like a stall.
- A binding call that returns success but changes nothing usually targeted a driver id from a different resource. Ids are only unique within their parent — always qualify with the resource.

The full code table and the reason strings that qualify them are on the [error codes page](https://theassettrack.com/wialon-api/errors/).

## Where next

Driver data feeds everything that groups by person: the [report execution](https://theassettrack.com/wialon-api/reports/) behind eco-driving scores, the [notification engine](https://theassettrack.com/wialon-api/notifications/) for driver-specific alerts, and the [rate-limit-safe sync](https://theassettrack.com/blog/wialon-api-rate-limits-and-resilient-sync-design/) that keeps the binding history in your own database — which is what [FleetSQL](https://theassettrack.com/products/fleetsql/) exists to hold. If bindings are business-critical — payroll, billing, compliance — do not read them live per report; sync them on a schedule and join locally.

## Also in this reference

- ### Wialon API Token and Login: Sessions That Survive
 Wialon authorization end to end: the login form, token/login, token/update, the access-flag table, and the 100-day inaction rule that deletes idle tokens.
 [Wialon API Token and Login: Sessions That Survive](https://theassettrack.com/wialon-api/token/)
- ### Wialon API Errors: Codes 1, 4, 6, 7 and 1004
 The full Wialon Remote API error table, the 1003 reason variants, the quotas that produce each code, and how to classify them for retry logic.
 [Wialon API Errors: Codes 1, 4, 6, 7 and 1004](https://theassettrack.com/wialon-api/errors/)
- ### Wialon API in Postman: Authenticate in 10 Minutes
 The Wialon request format, the two headers and encodings that break every first call, and a Postman setup for an authenticated session.
 [Wialon API in Postman: Authenticate in 10 Minutes](https://theassettrack.com/wialon-api/postman/)
- ### Wialon API: Get a Unit's Last Position and Message
 Data flags, core/search_items, and the difference between last position and last message — the distinction behind the most-asked question on the SDK board.
 [Wialon API: Get a Unit's Last Position and Message](https://theassettrack.com/wialon-api/units/)
- ### Wialon API Reports: exec_report Without the Errors
 One report per session, the cleanup_result rule, the calls that cannot run alongside it, and the time limit that returns no rows instead of an error.
 [Wialon API Reports: exec_report Without the Errors](https://theassettrack.com/wialon-api/reports/)
- ### Wialon API Notifications: Create, Edit, Enable
 resource/update_notification end to end — call modes, the trigger and action pair, schedules, and the response fields that make notifications diffable.
 [Wialon API Notifications: Create, Edit, Enable](https://theassettrack.com/wialon-api/notifications/)
- ### Wialon Retranslator: Protocols and Configuration
 The nine retranslation protocols Wialon can forward to, the update_config parameters each one uses, and where retranslation fits against an API pull.
 [Wialon Retranslator: Protocols and Configuration](https://theassettrack.com/wialon-api/retranslator/)
