Create a device on Central, start the agent on the device, and make it show up as Healthy (정상) on the Edge Fleet screen. All output on this page comes from a real run. Only tokens and host names are hidden.

You need:

  • A device that has finished Install (a development PC works too)
  • A tenant ADMIN account — registering a device needs the SettingsADMIN permission
  • Outbound HTTPS from the device to the Central API address (for example https://mlops.example.com)

1. Register the device on Central

  1. Open Edge Fleet (Edge Fleet) in the left menu and press Register device (디바이스 등록) at the top right.
  2. ① In Device ID (디바이스 ID), enter the device name (for example edge-bench-01). Letters, digits, ., _ and -, up to 64 characters. Location is optional. ② All five Token scopes (토큰 스코프) are on by default. If you are unsure, leave them. ③ Press Register (등록).
    Register device dialog — ① device ID ② token scopes (all by default) ③ Register
  3. The Registered (등록 완료) window shows the token only once. Copy it with the copy button and keep it somewhere safe. Once you close the window you cannot see it again; if you lose it, you must issue a new one with Rotate (회전) in Token management (토큰 관리) on the device detail page.

Right after registration the device is Pending (연결 대기). It becomes Healthy (정상) once the device sends its first heartbeat.

ScopeScreen nameAllowed calls
telemetry:writeTelemetry (텔레메트리)Heartbeats, sending collected records
inference:writeInference (추론)Sending inference results
container:pullContainer (컨테이너)Looking up model container images
models:readModels (모델)Model list, versions, artifact downloads
data:writeFiles (파일)Chunked upload of files (images and so on)

2. Write the config file on the device

Keep the token in an environment variable, not in the file. Config files easily end up in repositories and backups.

# /etc/geo-mlops/edge.env  (chmod 600)
GEO_EDGE_CENTRAL__TOKEN=<device-token>
# /etc/geo-mlops/edge.yaml
central:
  base_url: https://mlops.example.com   # Central API address

device:
  id: edge-bench-01        # match the device ID on the screen to avoid confusion
  location: bench

data_dir: /var/lib/geo-mlops-edge   # queue, files and model cache pile up here

api:
  host: 127.0.0.1          # 0.0.0.0 if you want to view it from a tablet on site
  port: 8600

# Keep these short while testing. In production use the defaults (30 s / 25 s)
heartbeat_interval_s: 5
commands_poll_s: 10

collectors:
  # Entry point where other programs push records through the local API
  - type: push
    name: robot-1
    priority: 60
    options:
      kind: robot

  # Upload JPEGs dropped by the camera as files
  - type: watchdir
    name: cam-0
    priority: 20
    options:
      path: /data/incoming
      pattern: "*.jpg"

3. Run the agent

set -a; . /etc/geo-mlops/edge.env; set +a
geo-mlops-edge --config /etc/geo-mlops/edge.yaml run

If logs like these appear within a few seconds, it worked.

INFO    geo_mlops_sdk.edge.daemon: starting geo-mlops-edge (data_dir=/var/lib/geo-mlops-edge, central=https://mlops.example.com)
INFO    geo_mlops_sdk.edge.runtime: edge runtime started as edge-bench-01
INFO:     Uvicorn running on http://127.0.0.1:8600 (Press CTRL+C to quit)
INFO    geo_mlops_sdk.edge.link: link offline -> probing
INFO    geo_mlops_sdk.edge.link: link probing -> online
INFO    httpx: HTTP Request: POST https://mlops.example.com/api/v1/edge/register "HTTP/1.1 200 OK"
INFO    geo_mlops_sdk.edge.runtime: registered with Central as edge-bench-01 (ACTIVE)
INFO    httpx: HTTP Request: POST https://mlops.example.com/api/v1/edge/heartbeat "HTTP/1.1 200 OK"

The link state goes offline → probing → online. It takes two successes in a row to become online (link.online_after_ok), so the first registration takes 1–2 seconds.

4. Put some data in

In another terminal, push three records through the push entry point, then send one of the same ids again.

for i in 1 2 3; do
  curl -s -X PUT http://127.0.0.1:8600/api/v1/collectors/robot-1/records/evt-$i \
       -H 'content-type: application/json' \
       -d "{\"payload\": {\"step\": $i}}" -w ' %{http_code}\n'
done
curl -s -X PUT http://127.0.0.1:8600/api/v1/collectors/robot-1/records/evt-1 \
     -H 'content-type: application/json' -d '{"payload": {"step": 1}}' -w ' %{http_code}\n'
{"id":"robot-1:evt-1","kind":"robot","duplicate":false} 201
{"id":"robot-1:evt-2","kind":"robot","duplicate":false} 201
{"id":"robot-1:evt-3","kind":"robot","duplicate":false} 201
{"id":"robot-1:evt-1","kind":"robot","duplicate":true} 200

The fourth has an id that was already received, so the answer is 200 with duplicate: true, and it is not queued. Copy an image into /data/incoming and the cam-0 collector uploads it as a file.

Ask the agent for its current state.

geo-mlops-edge --config /etc/geo-mlops/edge.yaml status
{
  "device": {
    "id": "edge-bench-01",
    "location": "bench",
    "hostname": "edge-pc",
    "os": "Ubuntu 24.04.5 LTS x86_64",
    "agent_version": "0.2.0",
    "registered": true
  },
  "link": { "state": "online", "latency_ms": 4.26, "error": "" },
  "sync": { "state": "idle", "last_error": null, "denied": null },
  "backlog": { "count": 0, "bytes": 0, "evicted_24h": 0, "by_kind": {} },
  "collectors": [
    { "name": "robot-1", "type": "push", "state": "running", "error": null },
    { "name": "cam-0", "type": "watchdir", "state": "running", "error": null }
  ],
  "attention": []
}

(Some fields are trimmed for length.) If backlog.count is 0, everything has been sent to Central.

5. Check on the fleet screen

  1. In the Edge Fleet (Edge Fleet) list, ① the new device shows Healthy (정상), Backlog (대기) 0 and Sync (동기화) Idle (대기).
    Edge Fleet — ① a device with a running agent shows Healthy, zero backlog and an idle sync
  2. Click the row to open the detail page. It shows ① the SDK and agent versions ② the backlog and the last send time ③ the device's local models ④ the state of each collector.
    Device overview — ① SDK and agent versions ② backlog and sync ③ local models ④ collector status
  3. The Collected data (수집 데이터) tab shows the records you just pushed, by kind (robot, http …). ① Narrow it with the kind filter.
    Collected data tab — records from each collector, by kind. ① kind filter

The Files (파일) tab collects the files uploaded by watchdir, and the Inference results (추론 결과) tab collects the inferences run on the device (Models and inference).

Files tab — files sent by the watchdir collector and their chunked-transfer state

Stopping

Stop it with Ctrl-C (or SIGTERM). It finishes the chunk it was sending, returns the queue items it had claimed, closes the DB, and exits.

INFO:     Finished server process [2063519]
INFO    geo_mlops_sdk.edge.runtime: edge runtime stopped

When heartbeats stop and 3 minutes pass (the server default), the device turns Unhealthy (비정상). In production, run it permanently with the systemd unit or a container from Deploy.

Written for the platform as of 2026-09-21.

© Geo-MLOps