Show timestamps on conversation messages
Open 💬 35 comments Opened Apr 7, 2026 by quad341
Feature request
Add an option to display timestamps on user and assistant messages in the conversation.
Use case
When monitoring long-running agent work (e.g., checking on background workers every 5 minutes via a cron loop), it's hard to tell how long ago earlier parts of the conversation happened. A timestamp on each message turn would make it easy to:
- See when a health check last ran
- Know how long ago you gave an instruction
- Correlate conversation events with external logs/processes
- Generally orient yourself in a long-running session
Proposed behavior
A setting (e.g., showTimestamps: true in settings.json) that renders a timestamp next to each user prompt and assistant response. Something like:
[09:15:32] > check worker status
[09:15:34] Both workers are active...
[09:20:32] > check worker status
[09:20:33] gc-694 finished, gc-695 still running...
Relative timestamps (e.g., "5m ago") would also work, though absolute times are easier to cross-reference with external systems.
Alternatives considered
- Status line: Can show current time but not per-message history
- UserPromptSubmit hook: Could inject timestamps into prompt text, but pollutes the actual message content
35 Comments
I built a plugin that addresses this as a workaround until native support lands:
claude-code-timestamps — adds a
/timestampscommand that displays a timestamped message timeline from your current session's transcript data.A native UI integration would obviously be better, but this can help in the meantime.
this is beautiful. thank you!
Would this be something the Assistant could see? It would be helpful for Claude to know how long has elapsed between user messages. (e.g. I'm doing DNS work right now and it would be great for Claude to be able to factor into its reasoning, "It's been 3 hours and the TTL was set to 5 hours so we're still within the cache refresh time.")
Would really like this built-in as well, but another workaround for now is to add this to your CLAUDE.md:
I have had scenarios where it would be beneficial to know when I prompted something. I would also like to add date + time, because I am a messy person who has too many chat tabs.
My agent said:
+1 - Really useful for long-running sessions with background tasks (builds, deploys, CI). When multiple things run in parallel it's hard to correlate what happened when.
Currently working around this with a UserPromptSubmit hook that injects the current timestamp, but per-message timestamps in the UI would be much better.
A toggle in settings (e.g."showTimestamps": true) that adds a subtle timestamp next to each message/tool output would cover it.
Not quite what you're asking for (this doesn't render per-message timestamps in the transcript), but I made a plugin for the adjacent problem and it might scratch part of the itch. What you see:
[after 5m 2s]note when you send a prompt after >1 minute idleThe model itself also gets hidden timing context each turn (time, idle seconds, last-turn duration), so if you just want the model to be time-aware this covers that. If seeing the time in the transcript itself is what matters, a small
Stophook emitting asystemMessagewith the timestamp would work too — the plugin uses the same mechanism for the idle note.Repo: https://github.com/clankercode/claude-inject-idle-time
Adding a web UI / iOS / multi-day-session perspective I don't see covered in the thread yet.
Not just the terminal TUI. This gap also exists on the web UI at
claude.ai/codeand in the Claude iOS app. Both render the chat as a vertical scroll with no timestamps on individual messages, so on multi-day sessions you can't tell when any given exchange happened. When this lands, please scope all three surfaces (CLI TUI + web + iOS), not only the CLI.Real-world use. I run Claude Code sessions that span 3–7 days continuously (architecture firm, rolling project context with daily check-ins). A typical day mixes
おはよう/寝ますgreetings, scheduled Routines, build triggers, and follow-ups. Scrolling back to "what did I ask on Tuesday?" is pure guesswork right now. Standard messaging apps (LINE, iMessage, Slack, WhatsApp) have shown per-message timestamps since around 2011 — this is baseline UX for anything people use as a conversation.Workaround I'm running, as a concrete implementation example. I have Claude stamp every response itself via
CLAUDE.md:Rendered output looks like:
It works once the model is instructed, but:
A platform-level timestamp — even just hover-to-reveal on each message — removes all of that friction in one change, and is ground-truth instead of model-reported.
Related but distinct. #47160 asks for exposing timestamps to the model (context layer). This issue is about displaying timestamps to the user (presentation layer) — both should land, but they're different fixes. My earlier #49692 tried to bundle them and was closed as a duplicate of #47160; I'm adding this perspective here rather than re-filing, since the UI layer is the concern of #44763.
For the model-facing side of this (Claude knowing what time it is), there's a working plugin workaround: claude-inject-idle-time — injects timing context via \
UserPromptSubmit\hook. I've opened a PR adding MCP time query tools and session timeline logging.The UI timestamp display (what this issue specifically requests) still needs upstream support — can't render timestamps in the TUI from a plugin.
Mockup of how this could look in the TUI:
!timestamp-mock
Per-message timestamps (①) and tool durations (②) need upstream support. Idle gap indicator (③) and statusline clock (④) are achievable today via the idle-timing plugin.
cc @clankercode
I don't really care how you do it, but I would love for it to be a built-in to have timestamps on user prompts when they're submitted and when Claude hands back off to the user for input.
Community workaround: I combined two community plugins into a single fork that covers this: pleasedodisturb/claude-inject-idle-time.
Sourced from:
Also includes passive time injection (hooks), active time queries (MCP server), and a statusline elapsed timer.
Install:
claude plugin add --from https://github.com/pleasedodisturb/claude-inject-idle-timeI too would LOVE this enhancement!
Timestamps and ability to copy messages are two very basic yet very needed features that are missing from CC for VS Code too. We really need this.
I'm adding to the request, using the VS Code Plugin and I'm missing it - for now I'm surviving with the global rule.
Until this is built in, here's a plugin that shows local-time
[HH:MM:SS]on every message via aMessageDisplayhook — and can optionally make Claude itself time-aware: https://github.com/zoharbabin/claude-code-message-timestamps/plugin marketplace add zoharbabin/claude-code-message-timestampsthen/plugin install message-timestamps@zoharbabin-claude-tools— cross-OS, MIT. (see #2441)Now I need to also merge Zohar's fix into my mixfix 😁😁
Update on the merged fork from April: it's now a standalone plugin, chronoclaude (v0.5.2, MIT), combining the pieces that surfaced in this thread plus one more:
[HH:MM:SS]on every assistant message, rendered in the TUI via theMessageDisplayhook (Claude Code 2.1.152+), adapted from zoharbabin/claude-code-message-timestamps. In April I wrote that per-message timestamps needed upstream support; the hook API has since made this possible from a plugin./timestampsretrospective session timeline, from s-a-s-k-i-a/claude-code-timestamps (posted earlier in this thread)[after 5m 2s]), MCP time tools, and a statusline clock, from clankercode/claude-inject-idle-timeEach surface toggles independently via
CLAUDE_TIMING_*env vars (all on by default).Timestamps on your own prompts still need upstream support; the hook can only decorate assistant messages.
cc @zoharbabin @s-a-s-k-i-a @XertroV
Came here to request the same feature 🙏 I think a timestamp for each line would be too busy.
Summary
Session history in Claude Code currently shows no time or date information. When resuming or scrolling back through a session, there's no way to tell when a given exchange happened — whether it was five minutes ago or three days ago.
Proposal
Borrow the familiar Slack/iMessage pattern: lightweight day dividers between messages from different days, plus a small timestamp on each message.
Day dividers only appear when the day changes, so they add near-zero visual noise in a single continuous session but become genuinely useful across multi-day work.
Why it matters
Notes
Timestamp density could be configurable (per-message vs. per-turn-cluster) if per-message feels too busy, but even a minimal version would be a clear improvement over the current zero-information state.
@ericmmartin have you tried any of the implementations above?
@pleasedodisturb Thanks for the pointer to chronoclaude — I switched from
s-a-s-k-i-a/claude-code-timestampsbased on your comment.Quick feedback from a Windows user (Claude Code 2.1.165, VSCode extension + terminal TUI) — technical analysis done with the help of Claude Code itself:
/timestampsworks correctly via thepy -3launcher (notpython3, which resolves to the Windows Store stub on Windows). Retrospective timeline displays cleanly in chat.MessageDisplayhook — inline[HH:MM:SS]timestamps do not appear in either the VSCode extension panel or the terminal TUI, despitenpm installbeing run and the hook script producing correct output when called directly (node message-display.jswith sample input returns the expected JSON with ANSI timestamp). No errors visible anywhere.So to answer the question on #68538: chronoclaude partially solves it. The retrospective
/timestampssurface works; the real-time inline timestamps don't — at least not on Windows. Not sure if this is a Windows-specific gap in the hook implementation or something else.Happy to share more diagnostics if useful — further investigation will also be done with Claude's help, so replies may include additional technical detail as we dig deeper.
@Non-Dev-Contributor they should, try turning them on, all I did was combine all the existing workarounds and added a toggle for each feature (also made the inline timecode dark)
@pleasedodisturb Thanks for the pointer — I verified the toggles:
CLAUDE_TIMING_MESSAGE_DISPLAYis not set (= on by default),noderuns correctly, andmessage-display.jsproduces valid output when invoked directly. The other hooks (UserPromptSubmit,PreCompact,Stop) all fire correctly.The
MessageDisplayhook specifically does not fire. Setup: Claude Code 2.1.165, Windows 11, VSCode extension (not the terminal TUI). My suspicion is thatMessageDisplayis implemented in the terminal/TUI but not in the VSCode extension panel on Windows. Can you confirm whether your setup is the VSCode extension or the terminal? If it's terminal-only, that would explain the gap.@Non-Dev-Contributor weird, for me it works on 2 machines, but let me fix it now
<img width="1059" height="152" alt="Image" src="https://github.com/user-attachments/assets/fa28a546-02a3-44e5-ba26-007363553322" />
@Non-Dev-Contributor ah, I'll see if we can workaround this, but you're right
<img width="1067" height="430" alt="Image" src="https://github.com/user-attachments/assets/a3404450-dbbe-401a-9097-c66af13449e1" />
Can you test in terminal, just to be sure?
Update — v2 of claude-code-timestamps is out, reworked from the feedback in this thread:
/timestampstimeline — day dividers + idle-gap markers (⋯ 4h 12m later ⋯), tool-call noise hidden by default,seconds/toolsoptions. It locates the session transcript by the recorded working directory, fixing a case where paths containing spaces found nothing.[HH:MM:SS](experimental) on each assistant message via theMessageDisplayhook — it's display-only, so it costs 0 tokens**: the marker is drawn on screen but never enters the transcript or the model's context. Toggle with/timestamps inline on|off.UserPromptSubmithook — off by default, so the plugin is token-free unless you opt in.Install:
/plugin marketplace add s-a-s-k-i-a/claude-code-timestamps→/plugin install chat-timestamps@chat-timestamps. Update later with/plugin marketplace update chat-timestamps+/plugin update.@pleasedodisturb @pleasedodisturb Follow-up on the
systemMessagediagnostic question: no, the idle note never appears in the VS Code panel — confirmed after multiple idle periods across parallel sessions today.So the gap is wider than just
MessageDisplay: the VS Code extension suppresses both hook output channels:MessageDisplay— event never dispatched by the panelsystemMessage— hook fires correctly (we can confirmUserPromptSubmitruns), but the output is not rendered in the panel UIThis means
CLAUDE_TIMING_STOP_TIMESTAMP=1will also be dead on arrival for VS Code users — theStophook fires, but thesystemMessageoutput goes nowhere visible.Since neither channel works in the VS Code extension, this looks like a host-side gap worth a dedicated Anthropic issue rather than anything a plugin can work around. Happy to open one if that would help move it forward.
@pleasedodisturb @pleasedodisturb Update:
MessageDisplaydoes work in the VS Code panel on 2.1.181 — confirmed working now. But there's a nuance worth noting:It only works when the hook is registered directly in
~/.claude/settings.json, not when loaded via the plugin system (hooks/hooks.jsonin the plugin folder). Other hooks (UserPromptSubmit,PreCompact,Stop) load fine through the plugin, butMessageDisplayspecifically does not get wired when coming from a plugin'shooks.json.Workaround that works: add this directly to
~/.claude/settings.json:Clean
[HH:MM:SS]timestamps now appearing on every assistant message in the panel. Thanks for tracking this down — the 2.1.181 fix was the key piece.@Non-Dev-Contributor @pleasedodisturb Consolidating the full diagnostic for the record, in case it helps other VS Code Windows users:
What was needed to get
[HH:MM:SS]working in the VS Code panel:MessageDisplayis not dispatched by the VS Code panel on 2.1.165. Your fix was the key unlock.MessageDisplaydirectly in~/.claude/settings.json— even on 2.1.181, the hook does not fire when it comes from the plugin'shooks/hooks.json. All other hooks (UserPromptSubmit,PreCompact,Stop) load correctly through the plugin system;MessageDisplayspecifically needs a direct entry:``
json
``"hooks": {
"MessageDisplay": [{
"hooks": [{
"type": "command",
"command": "node /path/to/chronoclaude/scripts/message-display.js",
"timeout": 10
}]
}]
}
CLAUDE_TIMING_MESSAGE_DISPLAY_COLOR=none— without this, the panel renders the SGR escapes as literal text ([90m[13:20:16][0m). Your entrypoint-aware colour fix isn't onmasteryet, so this is the interim workaround.After all three: clean
[HH:MM:SS]on every assistant message in the VS Code panel. Two of the three steps are workarounds for things that should ideally be transparent — the plugin hook wiring gap in particular seems worth a separate issue if you're not already tracking it.Resolved on the plugin side — shipped in chronoclaude v0.5.3 Full write-up since the thread got spread across a few comments:
What it actually was. The reported "no per-message timestamp in the IDE panel" was version-specific:
MessageDisplaydidn't fire in the VS Code panel on 2.1.165 (the build this was filed against), but it does on current builds (verified 2.1.181) — so that part looks fixed upstream in between. Testing in the actual panel then surfaced the real remaining bug: the plugin's grey[HH:MM:SS]marker emitted ANSI/SGR colour codes, and the VS Code panel renders those as literal[90m…[0mtext instead of colour (a real terminal renders them fine).The fix. Detect the client via
CLAUDE_CODE_ENTRYPOINT(cli/unset ⇒ terminal ⇒ colour;claude-vscode,remote*, … ⇒ plain) and emit a plain[HH:MM:SS]marker on non-terminal surfaces. Colour still applies in real terminals (including VS Code's integrated terminal and the JetBrains terminal tool window). Verified end-to-end in the panel.Update / install:
Two takeaways for anyone building on hooks:
MessageDisplayfires in the VS Code panel; on 2.1.165 it didn't.systemMessageoutput at all, and renders ANSI escapes indisplayContentas literal text. So a plugin's per-message UI has to go throughMessageDisplayas plain text —systemMessage-based approaches don't show in the panel.This is still a workaround — native per-message timestamps (this issue) would be the real fix, ideally scoped to web/iOS too. And I'm still after a JetBrains user to confirm rendering there: in the IDE terminal tool window, run
printenv CLAUDE_CODE_ENTRYPOINTand check whether the marker shows as grey colour vs a literal[90m…[0mleak. Thanks all.-----
cc @Non-Dev-Contributor @ericmmartin
Also, @s-a-s-k-i-a @zoharbabin @XertroV invited you as admins/collabs/owners to Chronoclaude, so may be we one day defork it into one thing (maybe yours:D)?
<img width="610" height="385" alt="Image" src="https://github.com/user-attachments/assets/c470834f-022d-4502-a974-6dce35e6caa6" />
@Non-Dev-Contributor thanks — that three-step breakdown is genuinely useful. Two notes:
CLAUDE_TIMING_MESSAGE_DISPLAY_COLOR=none) is no longer needed as of v0.5.3. Colour is now auto-suppressed in the panel (entrypoint-aware), so a fresh install renders a clean[HH:MM:SS]with no config.hooks/hooks.json) is the interesting one. On macOS the plugin-loadedMessageDisplayfired fine in the panel on 2.1.181 — so this looks host-side and possibly Windows-specific, rather than a plugin-manifest issue. A dedicated Anthropic issue is the right venue; if you open one I'll link it and add a Windows note to the README pointing at the manual-registration workaround in the meantime. Appreciate the thorough testing.@pleasedodisturb @pleasedodisturb After updating to v0.5.3 and removing the direct
settings.jsonhook entry (as the plugin-side fix implied it was no longer needed) — timestamps stopped working again after a full laptop restart.Re-adding the direct
settings.jsonMessageDisplayentry brought them back immediately, without even a VSCode restart.So the plugin hook wiring gap persists in v0.5.3 on this machine: the plugin's
hooks/hooks.jsonstill does not wireMessageDisplayeven after the update. The colour fix works (no[90m…[0mleak), but the hook registration via plugin system still doesn't fire forMessageDisplayspecifically.Setup for reference: Windows 11, VSCode extension 2.1.181, chronoclaude installed via
pluginsarray in~/.claude/settings.json(absolute path). The directsettings.jsonentry remains the working workaround — leaving it in place for now.@Non-Dev-Contributor confirmed — thank you, that pins it down. Our
hooks/hooks.jsonMessageDisplayentry is byte-identical in shape toUserPromptSubmit/Stop(which load fine via the plugin), so this is a host-side plugin-loader gap specific to theMessageDisplayevent, not something the plugin can fix. On macOS the plugin-loaded hook does fire, so it looks Windows- or install-method-specific.Two things done:
MessageDisplaydirectly in~/.claude/settings.jsonto bypass the plugin loader, exactly as you found. Thanks for keeping at it through the restart re-test.Feature request (VS Code extension): show date/time timestamps in the conversation view and the
/resumepickerWhen I resume an old session to understand when I did some work, there's no way to tell. The conversation view shows no timestamps, and the
/resumepicker only shows a relative time ("2 days ago"), not an absolute date. The data already exists — every line in the session.jsonlhas an ISO-8601 timestamp — it's just not surfaced in the UI.Requests
/resumepicker.Environment
<fill in><fill in>