quickdesk_audit table in ClickHouse. The console renders two
projections of that table:
Nothing on this screen mutates state. It is an audit surface: if a row
is missing or a session looks wrong, the cause is upstream in what the
device reported, not in the view.
Two event families: connection lifecycle and file transfer
The audit table mixes two kinds of events, and the two cards separate them. Connection lifecycle events mark the start and the end of a remote-control session. Both carry the samesession_id. The sessions
procedure groups on that id and pairs the opening event with the closing
one, so each console row is a session, not a raw event. A session that
has an opening event but no closing event is still returned — see
Sessions that never close.
File transfer events are standalone. Each row is one transfer
operation, tagged with a direction (send or recv) and carrying the
list of files it moved plus the filesystem path involved. There is no
open/close pairing here: one event is one complete record. The console
tags send transfers with a warning tone so that outbound movement off a
device is visually distinct from inbound.
Both families are scoped to a device (device_id) and, where the remote
end identified itself, to a peer (peer_id for transfers, ip for
sessions).
Field reference for an audit row
Session rows
adminQuickdesk.sessions returns one object per reconstructed session:
device_id and session_id together identify a row uniquely — the
console keys its table on the pair, so the same session_id observed
against two devices produces two rows.
The console formats durationSec as 12s, 4m 07s, or 1h 23m
depending on magnitude, and shows a live tag instead of a duration
whenever live is set.
File transfer rows
adminQuickdesk.files returns one object per transfer event:
numFiles and files are independent fields, and they can disagree.
numFiles is the count the device reported; files is the per-file
detail, which may be empty even when the count is non-zero. The console
treats them as separate: it always prints the count, and prints the
comma-joined name list only when files is non-empty.
The aggregate byte size shown next to the count is computed in the
console, not stored: it is the sum of the second element of every pair
in files. Because of that, the byte total reflects only the files that
appear in files. If per-file detail is missing, the size is suppressed
rather than shown as zero. Do not treat that total as an authoritative
transfer volume — treat files as the authority, and read the total as a
convenience sum of it.
How a session is reconstructed from open and close events
A session row in the console is derived, not stored:- The device emits a connection event when a remote-control session
starts. It carries
session_id,device_id, and the peerip. - The device emits a matching close event when the session ends,
carrying the same
session_id. adminQuickdesk.sessionsgroups the events bysession_idand emits one row:openedfrom the first event,durationSecfrom the difference between the two.- If step 2 never happened, the row comes back with
live: trueanddurationSec: null.
live flag means “no
close event has been recorded”, not “a connection is currently
established”. It is an inference from absence. The next section covers
why the two are not the same thing.
Sessions that never close
A session can sit in thelive state indefinitely. The common causes:
- The close event was never emitted. A device that loses power, is hard-killed, or drops its network link mid-session has no opportunity to report the close. The open event is already durable in the audit table; the pair never completes.
- The close event was emitted but not delivered. If the audit write fails or is dropped in transit, the same asymmetry results.
- The session genuinely is still open. A long-running unattended session looks identical to the two cases above.
live row from a real one, cross-check the
device’s current connection state on the device screen rather than
inferring it from this table.
A stale live row never resolves on its own. The close event is not
back-filled, so the row stays live for as long as it remains inside the
query window, and then falls out of the view.
Query windows, row caps, and retention
The console calls both procedures with fixed arguments:
Three things follow from this.
The windows differ by card on purpose. Sessions are an operational
signal — you look at them to understand what happened recently — so the
window is short. File transfers are a compliance signal, where “what
left this machine last month” is the question, so the window is longer.
A transfer that happened three weeks ago appears in Files shared but
its parent session will already have aged out of Sessions.
The row cap truncates silently. Each table returns at most 200 rows.
The screen has no pagination and no “showing N of M” indicator, so a busy
fleet will fill both tables to the cap and you will be looking at a
prefix of the trail, not the whole of it. When a table is exactly full,
assume there is more.
Neither number is a retention policy.
days bounds the query, not
the data. Rows older than the window still exist in quickdesk_audit;
they are simply not requested. How long they actually survive is a
property of the quickdesk_audit table in your ClickHouse deployment —
its TTL and partition-dropping configuration — and not something this
screen sets or reports. If you need a guaranteed retention period for an
audit or compliance requirement, verify it against the table definition
in your deployment, not against what this screen displays.
Exporting the trail outside the console
Two routes out, depending on what you need. Call the procedures directly. BothadminQuickdesk.sessions and
adminQuickdesk.files accept limit and days as inputs. The console
hardcodes 200/7 and 200/30, but a caller is free to pass different
values:
limit is a hard
ceiling on a single call rather than a page size.
Query ClickHouse directly. The underlying rows live in
quickdesk_audit. Reading that table yourself is the route for anything
the procedures do not express: arbitrary time ranges beyond a single
call’s limit, joins against your own inventory data, unpaired-event
analysis, or scheduled extracts into a warehouse. You are then working
with raw events rather than reconstructed sessions, so you own the
grouping on session_id.
Related
- Telemetry — the other operational data streams, including the ClickHouse CDR pipeline this trail sits alongside.
- Authentication — the API key scopes that
gate the
adminQuickdeskprocedures.

