package pier import ( "log/slog" "time" "git.golem15.com/golem15/summercms/modules/diary" ) // LogComponent is the diary component pier logs under. const LogComponent = "pier" // sessionPrefixLen is how much of a session id the audit lines show. const sessionPrefixLen = 8 // stateless is the session value of a call served on the stateless path. const stateless = "stateless" // logger is the module's logger (component pier). func logger() *slog.Logger { return diary.For(LogComponent) } // sessionPrefix shortens a session id for logging; a stateless call logs // "stateless" and a call served without a session on the stateful path // "ephemeral". func sessionPrefix(id string) string { if id == "" { return stateless } if id == ephemeralSession { return ephemeralSession } if len(id) > sessionPrefixLen { return id[:sessionPrefixLen] } return id } // logToolCall writes the one audit line per tool call (D-23): the tool, // its guard, the frontend user id (0 when none), the backend admin id (0 // when none), the OAuth client id, the token kind, the session prefix, the // route's status and the duration. Never the arguments, the body or a token. func logToolCall(log *slog.Logger, id Identity, t *tool, session string, status int, took time.Duration) { var userID, adminID uint var clientID string if id.Frontend != nil { userID = id.Frontend.UserID clientID = id.Frontend.ClientID } if id.Backend != nil { adminID = id.Backend.UserID if clientID == "" { clientID = id.Backend.ClientID } } log.Info("pier: tool call", "tool", t.name, "guard", t.guardName, "user_id", userID, "admin_id", adminID, "client_id", clientID, "token_kind", id.TokenKind, "session", sessionPrefix(session), "status", status, "duration_ms", took.Milliseconds(), ) } // logSession writes one line per session lifecycle step with the session // prefix and the binding, never the token. The steps: open (serveNew), // rehydrate (lookup), end (DELETE), binding_refused (another binding // presented the id), revoked (a revocation or deletion event), // stream_closed (a GET stream whose bearer or record is gone) and expired // (the reaper closed a local copy whose record expired). func logSession(log *slog.Logger, step, session, binding string) { log.Info("pier: session", "step", step, "session", sessionPrefix(session), "binding", binding) }