Audi E-Scooter GPS Tracker and Immobiliser

updated 8 min read #electronics #security

I added a GPS tracker with an immobiliser to my new Audi e-scooter. The tracker reports the scooter’s position to my own Traccar server, and an SMS to the tracker switches a relay that cuts power to the dashboard. This post covers the parts, the wiring, the installation and the configuration of the server and the tracker.

The scooter#

The Audi e-scooter is based on the Segway Ninebot MAX G30D II.

  • Speed: max. 20 km/h
  • Range: approx. 65 km
  • Weight: 19.1 kg
  • Payload: max. 100 kg
  • Dimensions unfolded: 116.7 × 47.2 × 120.3 cm
  • Dimensions folded: 116.7 × 47.2 × 53.4 cm
  • Brakes: drum brake (front), electric brake (rear)
  • Battery: 551 Wh lithium-ion
  • Charging time: 6 hours to 100 %
  • Motor: 350 W
  • Climbing ability: 20 %
  • Wheels: 10-inch (25.4 cm) tubeless pneumatic tyres
  • Item number: 89A050001B

Design goals#

  • Switch the scooter off by SMS or app when it is parked.
  • Leave the original wiring harness intact. The relay sits in a custom adapter cable between the controller and the dashboard.
  • Make the modification removable without a trace. For a warranty or insurance claim, the scooter has to be unmodified.

Parts#

Wiring diagram#

Wiring diagram: the 36 V battery feeds the controller through an XT60 Y-cable whose JST branch powers the GPS tracker through a fuse; the tracker switches a Finder relay that is looped into the controller-to-dashboard cable via PAP-07V-S and PALR-07VF connectors
Wiring diagram of the GPS tracker in the Audi MAX G30D II

The wire labelled “GPS antenna” in the diagram is really the tracker’s ignition detection input, which responds to +12 V. I don’t need ignition detection, so I reused that wire as an antenna extension. The tracker housing opens easily and the GPS antenna inside is only glued in. I removed it, soldered one end of the orange wire to the antenna pads and the antenna to the other end. Now the antenna can sit anywhere in the scooter where the GPS reception is better; the diagram suggests leading it out into the rear mudguard.

Installation#

  1. Remove the underbody from the scooter.
  2. Disconnect the battery at the XT60 connector. You may break a warranty seal here.
  3. Install the Y-cable.
  4. Solder the JST socket to the red and black wires of the tracker harness and insulate it with heat-shrink tubing.
  5. Insert the SIM card into the tracker and connect the tracker to the Y-cable.
  6. Set up the tracker as described in its manual (APN, phone number and so on; see below).
  7. Connect the relay to the tracker’s positive wire, behind the fuse, with a Scotchlok connector.
  8. Connect the other end of the relay coil to the tracker’s yellow wire (relay output, labelled GND in the diagram) with a Scotchlok connector. The tracker pulls this wire to ground when you send the lock command.
  9. Build the adapter cable with the JST connectors, so the original dashboard cable stays undamaged. The relay is looped in through this adapter. The yellow, red and black wires connect 1:1; the green wire goes through the normally closed contact of the relay.
  10. Optionally pot the relay in the box with casting resin. Secure all cables with foam when you install them.
  11. Reassemble the scooter.

Build log#

The JST leads were delayed by the chip shortage, so I first built and tested the circuit without the dashboard cut-off.

Tracker harness on a white work mat: red and black power leads with a JST plug and a blade fuse holder, and a white relay connected by red and black wires
Wiring without the dashboard cut-off
HP E3611A bench power supply showing 11.4 V and 0.05 A, connected to the SinoTrack tracker and the relay on the work mat
First test of the circuit on the bench power supply

The first test was successful. The relay only switches above 36 V, while the tracker works with anything between 9 and 60 V.

Bench power supply display reading 24.0 V and 0.02 A
The tracker sleeping at 480 mW

The circuit draws 480 mW while the tracker sleeps and peaks at 780 mW. Before you store the scooter for the winter, disconnect the tracker from the battery to prevent a deep discharge.

When the JST leads arrived, I built the final wiring with the adapter cable for the dashboard connection.

Finished harness on the work mat: the SinoTrack tracker, fuse, relay and the 7-pin JST adapter cable with white connectors at both ends
Final harness with relay and dashboard adapter cable

The connectors are on the controller board, under a massive steel cover that has to be unscrewed first.

Open controller housing in the scooter deck, with the green circuit board, thick phase wires and the XT60 battery connector in front
The opened controller

The connector marked with a red dot leads to the dashboard.

Close-up of white connectors on the controller board; the dashboard connector is marked with a red dot
Dashboard connector on the controller board
The tracker harness and adapter cable connected to the open controller next to the scooter, before installation
Final wiring during the first test with the scooter

The modified circuit worked on the first try. Finally, I tucked the circuit into the deck next to the battery and controller before mounting the underbody.

Inside of the scooter deck with the battery, the controller and the neatly routed tracker cables, fuse and relay
Final installation before mounting the underbody

Traccar server#

Traccar is a free and open-source GPS tracking server. In this project it replaces the SinoTrack servers, because I don’t want to store my location data on servers in China. This step is optional, and running your own server securely takes some technical know-how.

I deploy Traccar with Podman instead of Docker. Rather than a Compose file, I use a pod that systemd starts and controls. I prefer Podman because the containers run entirely without elevated privileges.

First, extract the default configuration from the image:

podman run --rm \
  --entrypoint cat \
  docker.io/traccar/traccar:6.16.0 \
  /opt/traccar/conf/traccar.xml > traccar.xml

For Docker users, here is an equivalent Compose file. The image tags were current in October 2026; check for newer releases before you use them. Replace the placeholder passwords.

services:
  mariadb:
    image: docker.io/library/mariadb:12.3.3
    restart: unless-stopped
    environment:
      MARIADB_DATABASE: traccar
      MARIADB_USER: traccar
      MARIADB_PASSWORD: CHANGE-ME-traccar-db-password  # placeholder
      MARIADB_ROOT_PASSWORD: CHANGE-ME-root-password   # placeholder
    volumes:
      - ${HOME}/traccar/database:/var/lib/mysql:rw

  traccar:
    image: docker.io/traccar/traccar:6.16.0
    restart: unless-stopped
    depends_on:
      - mariadb
    ports:
      - "5013:5013"  # H02 protocol, used by the SinoTrack ST-901
      - "8082:8082"  # web interface
    volumes:
      - ${HOME}/traccar/traccar.xml:/opt/traccar/conf/traccar.xml:ro
      - ${HOME}/traccar/logs:/opt/traccar/logs:rw
      - ${HOME}/traccar/data:/opt/traccar/data:rw

By default, Traccar uses an embedded H2 database, which is not recommended for production. To use MariaDB instead, replace these lines in traccar.xml:

<entry key='database.driver'>org.h2.Driver</entry>
<entry key='database.url'>jdbc:h2:./data/database</entry>
<entry key='database.user'>sa</entry>
<entry key='database.password' />

with:

<entry key='database.driver'>com.mysql.cj.jdbc.Driver</entry>
<entry key='database.url'>jdbc:mysql://mariadb:3306/traccar?zeroDateTimeBehavior=round&amp;serverTimezone=UTC&amp;allowPublicKeyRetrieval=true&amp;useSSL=false&amp;allowMultiQueries=true&amp;autoReconnect=true&amp;useUnicode=yes&amp;characterEncoding=UTF-8&amp;sessionVariables=sql_mode=''</entry>
<entry key='database.user'>traccar</entry>
<entry key='database.password'>CHANGE-ME-traccar-db-password</entry>

With Compose, the database host is the service name mariadb. In a Podman pod, the containers share a network namespace, so use localhost instead.

Then start the stack. The web interface listens on port 8082. When I set this up, the default login was admin:admin; current Traccar versions have no default account, and the first user you register becomes the administrator.

If you run Traccar behind a reverse proxy such as nginx or an ingress controller, make sure WebSocket connections work. Otherwise the tracker is shown as online, but its pin never appears on the map. For nginx, add this to the location block:

proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";

GPS tracker configuration#

SIM card#

Two things matter most for the SIM card:

  • 2G (GPRS) support. The ST-901M only uses GPRS, so it does not work with LTE-only SIM cards.
  • No PIN. Without buttons or a screen, the tracker has no way to enter a PIN. Put the SIM card into a normal phone once and disable the PIN request.

2G is being switched off in Germany. Deutsche Telekom plans to shut down its GSM network on 30 June 2028. Vodafone and o2 (Telefónica) have also announced their 2G shutdowns for 2028. After that, a 2G-only tracker like the ST-901M no longer works on these networks. Check the plans of your network operator, and consider a tracker with LTE support for a new build.

I use a SIM card from Netzclub, which runs on the o2 network. The APN depends on your provider; look it up and replace it in the commands below.

Setup by SMS#

Charge the tracker over its micro-USB port and place it outdoors for good reception. When both LEDs (blue and orange) are lit continuously, the tracker has a mobile network connection and a GPS fix. Now send the setup commands by SMS to the tracker’s phone number, from any phone.

The commands have the format [COMMAND][PASSWORD] [VALUE]. The default password is 0000. Lines starting with > are the SMS I sent, lines starting with < are the replies:

> 8030000 pinternet.interkom.de
< SET OK
> 7100000
< SET OK
> 8040000 traccar.example.com 5013
< SET OK
> SLEEP0000 5
< OK
> RESTART
< RESTART OK
> RCONF
< (current configuration and device ID)
  • 710 switches the tracker from SMS mode (the default) to GPRS mode, so it reports to the server instead of only answering SMS.
  • 803 sets the APN.
  • 804 sets the server address and port.
  • RCONF prints the configuration.
  • SLEEP0000 5 turns on the power-saving sleep mode that RCONF lists as SLEEP MODE (off by default). The ST-901 manual does not document this command or its argument.

Finally, log in to Traccar and add the tracker: give it a name and enter the ID printed on its housing.

With these settings, the tracker sends its position every 5 minutes while the scooter moves. The interval is configurable; see the tracker’s manual.

Immobiliser#

To cut the connection between the dashboard and the controller, send an SMS to the tracker when you park the scooter:

  • Lock: 9400000
  • Unlock: 9410000

This makes the scooter unusable for a thief, at least for a while.

Conclusion#

The tracker and relay add GPS tracking and a remote immobiliser to the scooter without touching the original wiring harness, and everything can be removed again. The immobiliser does not replace a physical lock against theft. It does stop someone from simply riding away, changing the scooter’s firmware or powering up and damaging the motor. With the 2G shutdown in 2028, the SinoTrack ST-901M has a limited life in Germany; the rest of the design works with any tracker that can switch a relay.

Sources#

cd ~/projects