klaude-code 1.2.14__py3-none-any.whl → 1.2.15__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- klaude_code/command/thinking_cmd.py +1 -1
- klaude_code/llm/input_common.py +1 -1
- klaude_code/session/templates/export_session.html +8 -12
- klaude_code/ui/modes/repl/event_handler.py +2 -1
- klaude_code/ui/modes/repl/renderer.py +1 -3
- klaude_code/ui/renderers/metadata.py +49 -88
- klaude_code/ui/renderers/thinking.py +2 -2
- klaude_code/ui/renderers/tools.py +45 -1
- klaude_code/ui/rich/markdown.py +27 -11
- klaude_code/ui/rich/theme.py +12 -12
- {klaude_code-1.2.14.dist-info → klaude_code-1.2.15.dist-info}/METADATA +1 -1
- {klaude_code-1.2.14.dist-info → klaude_code-1.2.15.dist-info}/RECORD +14 -14
- {klaude_code-1.2.14.dist-info → klaude_code-1.2.15.dist-info}/WHEEL +0 -0
- {klaude_code-1.2.14.dist-info → klaude_code-1.2.15.dist-info}/entry_points.txt +0 -0
|
@@ -142,7 +142,7 @@ def _select_anthropic_thinking_sync() -> llm_param.Thinking | None:
|
|
|
142
142
|
use_jk_keys=False,
|
|
143
143
|
style=SELECT_STYLE,
|
|
144
144
|
).ask()
|
|
145
|
-
if result
|
|
145
|
+
if not result:
|
|
146
146
|
return llm_param.Thinking(type="disabled", budget_tokens=0)
|
|
147
147
|
return llm_param.Thinking(type="enabled", budget_tokens=result or 0)
|
|
148
148
|
except KeyboardInterrupt:
|
klaude_code/llm/input_common.py
CHANGED
|
@@ -149,7 +149,7 @@ def parse_message_groups(history: list[model.ConversationItem]) -> list[MessageG
|
|
|
149
149
|
for item in items:
|
|
150
150
|
if isinstance(item, (model.UserMessageItem, model.DeveloperMessageItem)):
|
|
151
151
|
if item.content:
|
|
152
|
-
group.text_parts.append(item.content)
|
|
152
|
+
group.text_parts.append(item.content + "\n")
|
|
153
153
|
if item.images:
|
|
154
154
|
group.images.extend(item.images)
|
|
155
155
|
groups.append(group)
|
|
@@ -9,19 +9,15 @@
|
|
|
9
9
|
href="data:image/svg+xml,<svg xmlns=%22http://www.w3.org/2000/svg%22 viewBox=%220 0 24 24%22 fill=%22none%22 stroke=%22%230851b2%22 stroke-width=%222%22 stroke-linecap=%22round%22 stroke-linejoin=%22round%22><polyline points=%2216 18 22 12 16 6%22></polyline><polyline points=%228 6 2 12 8 18%22></polyline></svg>"
|
|
10
10
|
/>
|
|
11
11
|
<link
|
|
12
|
-
href="https://cdn.jsdelivr.net/npm/@fontsource/
|
|
12
|
+
href="https://cdn.jsdelivr.net/npm/@fontsource/geist-sans/latin-400.css"
|
|
13
13
|
rel="stylesheet"
|
|
14
14
|
/>
|
|
15
15
|
<link
|
|
16
|
-
href="https://cdn.jsdelivr.net/npm/@fontsource/
|
|
16
|
+
href="https://cdn.jsdelivr.net/npm/@fontsource/geist-sans/latin-500.css"
|
|
17
17
|
rel="stylesheet"
|
|
18
18
|
/>
|
|
19
19
|
<link
|
|
20
|
-
href="https://cdn.jsdelivr.net/npm/@fontsource/
|
|
21
|
-
rel="stylesheet"
|
|
22
|
-
/>
|
|
23
|
-
<link
|
|
24
|
-
href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:ital,wght@0,400;0,500;0,700;1,400;1,500;1,700&family=IBM+Plex+Sans:ital,wght@0,400;0,500;0,700;1,400;1,500;1,700&display=swap"
|
|
20
|
+
href="https://cdn.jsdelivr.net/npm/@fontsource/geist-sans/latin-700.css"
|
|
25
21
|
rel="stylesheet"
|
|
26
22
|
/>
|
|
27
23
|
<style>
|
|
@@ -39,9 +35,9 @@
|
|
|
39
35
|
--bg-error: #ffebee;
|
|
40
36
|
--bg-code: #f3f3f3;
|
|
41
37
|
--fg-inline-code: #4f4fc7;
|
|
42
|
-
--font-mono:
|
|
43
|
-
--font-markdown-mono:
|
|
44
|
-
--font-markdown: "
|
|
38
|
+
--font-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, Liberation Mono, Courier New, monospace;
|
|
39
|
+
--font-markdown-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, Liberation Mono, Courier New, monospace;
|
|
40
|
+
--font-markdown: "Geist Sans", system-ui, sans-serif;
|
|
45
41
|
--font-weight-bold: 800;
|
|
46
42
|
--font-size-xs: 13px;
|
|
47
43
|
--font-size-sm: 14px;
|
|
@@ -114,7 +110,7 @@
|
|
|
114
110
|
|
|
115
111
|
.meta-value {
|
|
116
112
|
font-family: var(--font-mono);
|
|
117
|
-
font-size: var(--font-size-
|
|
113
|
+
font-size: var(--font-size-xs);
|
|
118
114
|
color: var(--text);
|
|
119
115
|
overflow: hidden;
|
|
120
116
|
text-overflow: ellipsis;
|
|
@@ -1199,7 +1195,7 @@
|
|
|
1199
1195
|
mermaid.initialize({
|
|
1200
1196
|
startOnLoad: true,
|
|
1201
1197
|
theme: "neutral",
|
|
1202
|
-
fontFamily: '
|
|
1198
|
+
fontFamily: 'ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, Liberation Mono, Courier New, monospace',
|
|
1203
1199
|
});
|
|
1204
1200
|
</script>
|
|
1205
1201
|
<script>
|
|
@@ -9,7 +9,7 @@ from klaude_code import const
|
|
|
9
9
|
from klaude_code.protocol import events
|
|
10
10
|
from klaude_code.ui.core.stage_manager import Stage, StageManager
|
|
11
11
|
from klaude_code.ui.modes.repl.renderer import REPLRenderer
|
|
12
|
-
from klaude_code.ui.rich.markdown import MarkdownStream
|
|
12
|
+
from klaude_code.ui.rich.markdown import MarkdownStream, ThinkingMarkdown
|
|
13
13
|
from klaude_code.ui.rich.theme import ThemeKey
|
|
14
14
|
from klaude_code.ui.terminal.notifier import Notification, NotificationType, TerminalNotifier
|
|
15
15
|
from klaude_code.ui.terminal.progress_bar import OSC94States, emit_osc94
|
|
@@ -318,6 +318,7 @@ class DisplayEventHandler:
|
|
|
318
318
|
console=self.renderer.console,
|
|
319
319
|
spinner=self.renderer.spinner_renderable(),
|
|
320
320
|
indent=2,
|
|
321
|
+
markdown_class=ThinkingMarkdown,
|
|
321
322
|
)
|
|
322
323
|
self.thinking_stream.start(mdstream)
|
|
323
324
|
self.renderer.spinner_stop()
|
|
@@ -145,9 +145,7 @@ class REPLRenderer:
|
|
|
145
145
|
case events.AssistantMessageEvent() as e:
|
|
146
146
|
if is_sub_agent:
|
|
147
147
|
continue
|
|
148
|
-
renderable = r_assistant.render_assistant_message(
|
|
149
|
-
e.content, code_theme=self.themes.code_theme
|
|
150
|
-
)
|
|
148
|
+
renderable = r_assistant.render_assistant_message(e.content, code_theme=self.themes.code_theme)
|
|
151
149
|
if renderable is not None:
|
|
152
150
|
self.print(renderable)
|
|
153
151
|
self.print()
|
|
@@ -9,6 +9,7 @@ from rich.text import Text
|
|
|
9
9
|
|
|
10
10
|
from klaude_code.protocol import events, model
|
|
11
11
|
from klaude_code.trace import is_debug_enabled
|
|
12
|
+
from klaude_code.ui.renderers.common import create_grid
|
|
12
13
|
from klaude_code.ui.rich.theme import ThemeKey
|
|
13
14
|
from klaude_code.ui.utils.common import format_number
|
|
14
15
|
|
|
@@ -24,163 +25,123 @@ def _get_version() -> str:
|
|
|
24
25
|
def _render_task_metadata_block(
|
|
25
26
|
metadata: model.TaskMetadata,
|
|
26
27
|
*,
|
|
27
|
-
|
|
28
|
+
is_sub_agent: bool = False,
|
|
28
29
|
show_context_and_time: bool = True,
|
|
29
|
-
) ->
|
|
30
|
+
) -> RenderableType:
|
|
30
31
|
"""Render a single TaskMetadata block.
|
|
31
32
|
|
|
32
33
|
Args:
|
|
33
34
|
metadata: The TaskMetadata to render.
|
|
34
|
-
|
|
35
|
+
is_sub_agent: Whether this is a sub-agent block.
|
|
35
36
|
show_context_and_time: Whether to show context usage percent and time.
|
|
36
37
|
|
|
37
38
|
Returns:
|
|
38
|
-
|
|
39
|
+
A renderable for this metadata block.
|
|
39
40
|
"""
|
|
41
|
+
grid = create_grid()
|
|
42
|
+
|
|
40
43
|
# Get currency symbol
|
|
41
44
|
currency = metadata.usage.currency if metadata.usage else "USD"
|
|
42
45
|
currency_symbol = "¥" if currency == "CNY" else "$"
|
|
43
46
|
|
|
44
|
-
#
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
)
|
|
50
|
-
model_text = Text()
|
|
51
|
-
model_text.append_text(prefix).append_text(Text(metadata.model_name, style=ThemeKey.METADATA_BOLD))
|
|
47
|
+
# First column: mark only
|
|
48
|
+
mark = Text("└", style=ThemeKey.METADATA_DIM) if is_sub_agent else Text("•", style=ThemeKey.METADATA_BOLD)
|
|
49
|
+
|
|
50
|
+
# Second column: model@provider / tokens / cost / ...
|
|
51
|
+
content = Text()
|
|
52
|
+
content.append_text(Text(metadata.model_name, style=ThemeKey.METADATA_BOLD))
|
|
52
53
|
if metadata.provider is not None:
|
|
53
|
-
|
|
54
|
+
content.append_text(Text("@", style=ThemeKey.METADATA)).append_text(
|
|
54
55
|
Text(metadata.provider.lower().replace(" ", "-"), style=ThemeKey.METADATA)
|
|
55
56
|
)
|
|
56
57
|
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
# Line 2: Token consumption, Context, TPS, Cost
|
|
60
|
-
parts2: list[Text] = []
|
|
58
|
+
# All info parts (tokens, cost, context, etc.)
|
|
59
|
+
parts: list[Text] = []
|
|
61
60
|
|
|
62
61
|
if metadata.usage is not None:
|
|
63
|
-
#
|
|
64
|
-
|
|
65
|
-
("
|
|
66
|
-
(format_number(metadata.usage.input_tokens), ThemeKey.
|
|
62
|
+
# Tokens: ↑37k c5k ↓907 r45k
|
|
63
|
+
token_parts: list[tuple[str, str]] = [
|
|
64
|
+
("↑", ThemeKey.METADATA_DIM),
|
|
65
|
+
(format_number(metadata.usage.input_tokens), ThemeKey.METADATA),
|
|
67
66
|
]
|
|
68
|
-
if metadata.usage.input_cost is not None:
|
|
69
|
-
input_parts.append((f"({currency_symbol}{metadata.usage.input_cost:.4f})", ThemeKey.METADATA_DIM))
|
|
70
|
-
parts2.append(Text.assemble(*input_parts))
|
|
71
|
-
|
|
72
|
-
# Cached
|
|
73
67
|
if metadata.usage.cached_tokens > 0:
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
if metadata.usage.cache_read_cost is not None:
|
|
79
|
-
cached_parts.append((f"({currency_symbol}{metadata.usage.cache_read_cost:.4f})", ThemeKey.METADATA_DIM))
|
|
80
|
-
parts2.append(Text.assemble(*cached_parts))
|
|
81
|
-
|
|
82
|
-
# Output
|
|
83
|
-
output_parts: list[tuple[str, str]] = [
|
|
84
|
-
("output:", ThemeKey.METADATA_DIM),
|
|
85
|
-
(format_number(metadata.usage.output_tokens), ThemeKey.METADATA_DIM),
|
|
86
|
-
]
|
|
87
|
-
if metadata.usage.output_cost is not None:
|
|
88
|
-
output_parts.append((f"({currency_symbol}{metadata.usage.output_cost:.4f})", ThemeKey.METADATA_DIM))
|
|
89
|
-
parts2.append(Text.assemble(*output_parts))
|
|
90
|
-
|
|
91
|
-
# Reasoning
|
|
68
|
+
token_parts.append((" c", ThemeKey.METADATA_DIM))
|
|
69
|
+
token_parts.append((format_number(metadata.usage.cached_tokens), ThemeKey.METADATA))
|
|
70
|
+
token_parts.append((" ↓", ThemeKey.METADATA_DIM))
|
|
71
|
+
token_parts.append((format_number(metadata.usage.output_tokens), ThemeKey.METADATA))
|
|
92
72
|
if metadata.usage.reasoning_tokens > 0:
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
(":", ThemeKey.METADATA_DIM),
|
|
97
|
-
(
|
|
98
|
-
format_number(metadata.usage.reasoning_tokens),
|
|
99
|
-
ThemeKey.METADATA_DIM,
|
|
100
|
-
),
|
|
101
|
-
)
|
|
102
|
-
)
|
|
73
|
+
token_parts.append((" r", ThemeKey.METADATA_DIM))
|
|
74
|
+
token_parts.append((format_number(metadata.usage.reasoning_tokens), ThemeKey.METADATA))
|
|
75
|
+
parts.append(Text.assemble(*token_parts))
|
|
103
76
|
|
|
104
77
|
# Cost
|
|
105
78
|
if metadata.usage is not None and metadata.usage.total_cost is not None:
|
|
106
|
-
|
|
79
|
+
parts.append(
|
|
107
80
|
Text.assemble(
|
|
108
|
-
(
|
|
109
|
-
("
|
|
110
|
-
(f"{currency_symbol}{metadata.usage.total_cost:.4f}", ThemeKey.METADATA_DIM),
|
|
81
|
+
(currency_symbol, ThemeKey.METADATA_DIM),
|
|
82
|
+
(f"{metadata.usage.total_cost:.4f}", ThemeKey.METADATA),
|
|
111
83
|
)
|
|
112
84
|
)
|
|
113
|
-
if parts2:
|
|
114
|
-
line2 = Text(" / ", style=ThemeKey.METADATA_DIM).join(parts2)
|
|
115
|
-
renderables.append(Padding(line2, (0, 0, 0, indent + 2)))
|
|
116
|
-
|
|
117
|
-
parts3: list[Text] = []
|
|
118
85
|
if metadata.usage is not None:
|
|
119
86
|
# Context (only for main agent)
|
|
120
87
|
if show_context_and_time and metadata.usage.context_usage_percent is not None:
|
|
121
88
|
context_size = format_number(metadata.usage.context_size or 0)
|
|
122
|
-
|
|
89
|
+
parts.append(
|
|
123
90
|
Text.assemble(
|
|
124
|
-
(
|
|
125
|
-
("
|
|
126
|
-
(
|
|
127
|
-
f"{context_size}({metadata.usage.context_usage_percent:.1f}%)",
|
|
128
|
-
ThemeKey.METADATA_DIM,
|
|
129
|
-
),
|
|
91
|
+
(context_size, ThemeKey.METADATA),
|
|
92
|
+
(f" ({metadata.usage.context_usage_percent:.1f}%)", ThemeKey.METADATA_DIM),
|
|
130
93
|
)
|
|
131
94
|
)
|
|
132
95
|
|
|
133
96
|
# TPS
|
|
134
97
|
if metadata.usage.throughput_tps is not None:
|
|
135
|
-
|
|
98
|
+
parts.append(
|
|
136
99
|
Text.assemble(
|
|
100
|
+
(f"{metadata.usage.throughput_tps:.1f} ", ThemeKey.METADATA),
|
|
137
101
|
("tps", ThemeKey.METADATA_DIM),
|
|
138
|
-
(":", ThemeKey.METADATA_DIM),
|
|
139
|
-
(f"{metadata.usage.throughput_tps:.1f}", ThemeKey.METADATA_DIM),
|
|
140
102
|
)
|
|
141
103
|
)
|
|
142
104
|
|
|
143
105
|
# Duration
|
|
144
106
|
if show_context_and_time and metadata.task_duration_s is not None:
|
|
145
|
-
|
|
107
|
+
parts.append(
|
|
146
108
|
Text.assemble(
|
|
147
|
-
("
|
|
148
|
-
("
|
|
149
|
-
(f"{metadata.task_duration_s:.1f}s", ThemeKey.METADATA_DIM),
|
|
109
|
+
(f"{metadata.task_duration_s:.1f}", ThemeKey.METADATA),
|
|
110
|
+
("s", ThemeKey.METADATA_DIM),
|
|
150
111
|
)
|
|
151
112
|
)
|
|
152
113
|
|
|
153
114
|
# Turn count
|
|
154
115
|
if show_context_and_time and metadata.turn_count > 0:
|
|
155
|
-
|
|
116
|
+
parts.append(
|
|
156
117
|
Text.assemble(
|
|
157
|
-
(
|
|
158
|
-
("
|
|
159
|
-
(str(metadata.turn_count), ThemeKey.METADATA_DIM),
|
|
118
|
+
(str(metadata.turn_count), ThemeKey.METADATA),
|
|
119
|
+
(" turns", ThemeKey.METADATA_DIM),
|
|
160
120
|
)
|
|
161
121
|
)
|
|
162
122
|
|
|
163
|
-
if
|
|
164
|
-
|
|
165
|
-
|
|
123
|
+
if parts:
|
|
124
|
+
content.append_text(Text(" · ", style=ThemeKey.METADATA_DIM))
|
|
125
|
+
content.append_text(Text(" · ", style=ThemeKey.METADATA_DIM).join(parts))
|
|
166
126
|
|
|
167
|
-
|
|
127
|
+
grid.add_row(mark, content)
|
|
128
|
+
return grid if not is_sub_agent else Padding(grid, (0, 0, 0, 2))
|
|
168
129
|
|
|
169
130
|
|
|
170
131
|
def render_task_metadata(e: events.TaskMetadataEvent) -> RenderableType:
|
|
171
132
|
"""Render task metadata including main agent and sub-agents, aggregated by model+provider."""
|
|
172
133
|
renderables: list[RenderableType] = []
|
|
173
134
|
|
|
174
|
-
renderables.
|
|
135
|
+
renderables.append(_render_task_metadata_block(e.metadata.main, is_sub_agent=False, show_context_and_time=True))
|
|
175
136
|
|
|
176
137
|
# Aggregate by (model_name, provider), sorted by total_cost descending
|
|
177
138
|
sorted_items = model.TaskMetadata.aggregate_by_model(e.metadata.sub_agent_task_metadata)
|
|
178
139
|
|
|
179
140
|
# Render each aggregated model block
|
|
180
141
|
for meta in sorted_items:
|
|
181
|
-
renderables.
|
|
142
|
+
renderables.append(_render_task_metadata_block(meta, is_sub_agent=True, show_context_and_time=False))
|
|
182
143
|
|
|
183
|
-
return Group(*renderables)
|
|
144
|
+
return Padding(Group(*renderables), (0, 0, 0, 1))
|
|
184
145
|
|
|
185
146
|
|
|
186
147
|
def render_welcome(e: events.WelcomeEvent, *, box_style: Box | None = None) -> RenderableType:
|
|
@@ -2,7 +2,7 @@ from rich.console import RenderableType
|
|
|
2
2
|
from rich.padding import Padding
|
|
3
3
|
from rich.text import Text
|
|
4
4
|
|
|
5
|
-
from klaude_code.ui.rich.markdown import
|
|
5
|
+
from klaude_code.ui.rich.markdown import ThinkingMarkdown
|
|
6
6
|
from klaude_code.ui.rich.theme import ThemeKey
|
|
7
7
|
|
|
8
8
|
|
|
@@ -30,7 +30,7 @@ def render_thinking(content: str, *, code_theme: str, style: str) -> RenderableT
|
|
|
30
30
|
return None
|
|
31
31
|
|
|
32
32
|
return Padding.indent(
|
|
33
|
-
|
|
33
|
+
ThinkingMarkdown(
|
|
34
34
|
_normalize_thinking_content(content),
|
|
35
35
|
code_theme=code_theme,
|
|
36
36
|
style=style,
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import json
|
|
2
2
|
from pathlib import Path
|
|
3
|
+
from typing import Any, cast
|
|
3
4
|
|
|
4
5
|
from rich.console import RenderableType
|
|
5
6
|
from rich.padding import Padding
|
|
@@ -58,6 +59,49 @@ def render_generic_tool_call(tool_name: str, arguments: str, markup: str = "•"
|
|
|
58
59
|
return grid
|
|
59
60
|
|
|
60
61
|
|
|
62
|
+
def render_bash_tool_call(arguments: str) -> RenderableType:
|
|
63
|
+
grid = create_grid()
|
|
64
|
+
tool_name_column = Text.assemble((">", ThemeKey.TOOL_MARK), " ", ("Bash", ThemeKey.TOOL_NAME))
|
|
65
|
+
|
|
66
|
+
try:
|
|
67
|
+
payload_raw: Any = json.loads(arguments) if arguments else {}
|
|
68
|
+
except json.JSONDecodeError:
|
|
69
|
+
summary = Text(
|
|
70
|
+
arguments.strip()[: const.INVALID_TOOL_CALL_MAX_LENGTH],
|
|
71
|
+
style=ThemeKey.INVALID_TOOL_CALL_ARGS,
|
|
72
|
+
)
|
|
73
|
+
grid.add_row(tool_name_column, summary)
|
|
74
|
+
return grid
|
|
75
|
+
|
|
76
|
+
if not isinstance(payload_raw, dict):
|
|
77
|
+
summary = Text(
|
|
78
|
+
str(payload_raw)[: const.INVALID_TOOL_CALL_MAX_LENGTH],
|
|
79
|
+
style=ThemeKey.INVALID_TOOL_CALL_ARGS,
|
|
80
|
+
)
|
|
81
|
+
grid.add_row(tool_name_column, summary)
|
|
82
|
+
return grid
|
|
83
|
+
|
|
84
|
+
payload: dict[str, object] = cast(dict[str, object], payload_raw)
|
|
85
|
+
|
|
86
|
+
summary = Text("", ThemeKey.TOOL_PARAM)
|
|
87
|
+
command = payload.get("command")
|
|
88
|
+
timeout_ms = payload.get("timeout_ms")
|
|
89
|
+
|
|
90
|
+
if isinstance(command, str) and command.strip():
|
|
91
|
+
summary.append(command.strip(), style=ThemeKey.TOOL_PARAM)
|
|
92
|
+
|
|
93
|
+
if isinstance(timeout_ms, int):
|
|
94
|
+
if summary:
|
|
95
|
+
summary.append(" ")
|
|
96
|
+
if timeout_ms >= 1000 and timeout_ms % 1000 == 0:
|
|
97
|
+
summary.append(f"{timeout_ms // 1000}s", style=ThemeKey.TOOL_TIMEOUT)
|
|
98
|
+
else:
|
|
99
|
+
summary.append(f"{timeout_ms}ms", style=ThemeKey.TOOL_TIMEOUT)
|
|
100
|
+
|
|
101
|
+
grid.add_row(tool_name_column, summary)
|
|
102
|
+
return grid
|
|
103
|
+
|
|
104
|
+
|
|
61
105
|
def render_update_plan_tool_call(arguments: str) -> RenderableType:
|
|
62
106
|
grid = create_grid()
|
|
63
107
|
tool_name_column = Text.assemble(("◎", ThemeKey.TOOL_MARK), " ", ("Update Plan", ThemeKey.TOOL_NAME))
|
|
@@ -461,7 +505,7 @@ def render_tool_call(e: events.ToolCallEvent) -> RenderableType | None:
|
|
|
461
505
|
case tools.MULTI_EDIT:
|
|
462
506
|
return render_multi_edit_tool_call(e.arguments)
|
|
463
507
|
case tools.BASH:
|
|
464
|
-
return
|
|
508
|
+
return render_bash_tool_call(e.arguments)
|
|
465
509
|
case tools.APPLY_PATCH:
|
|
466
510
|
return render_apply_patch_tool_call(e.arguments)
|
|
467
511
|
case tools.TODO_WRITE:
|
klaude_code/ui/rich/markdown.py
CHANGED
|
@@ -4,8 +4,10 @@ from __future__ import annotations
|
|
|
4
4
|
import contextlib
|
|
5
5
|
import io
|
|
6
6
|
import time
|
|
7
|
+
from collections.abc import Callable
|
|
7
8
|
from typing import Any, ClassVar
|
|
8
9
|
|
|
10
|
+
from rich import box
|
|
9
11
|
from rich.console import Console, ConsoleOptions, Group, RenderableType, RenderResult
|
|
10
12
|
from rich.live import Live
|
|
11
13
|
from rich.markdown import CodeBlock, Heading, Markdown
|
|
@@ -32,7 +34,16 @@ class NoInsetCodeBlock(CodeBlock):
|
|
|
32
34
|
word_wrap=True,
|
|
33
35
|
padding=(0, 1),
|
|
34
36
|
)
|
|
35
|
-
yield Panel.fit(syntax, padding=0,
|
|
37
|
+
yield Panel.fit(syntax, padding=(0, 0), style="markdown.code.block", box=box.SIMPLE)
|
|
38
|
+
|
|
39
|
+
|
|
40
|
+
class ThinkingCodeBlock(CodeBlock):
|
|
41
|
+
"""A code block for thinking content that uses grey styling instead of syntax highlighting."""
|
|
42
|
+
|
|
43
|
+
def __rich_console__(self, console: Console, options: ConsoleOptions) -> RenderResult:
|
|
44
|
+
code = str(self.text).rstrip()
|
|
45
|
+
text = Text("```\n" + code + "\n```")
|
|
46
|
+
yield text
|
|
36
47
|
|
|
37
48
|
|
|
38
49
|
class LeftHeading(Heading):
|
|
@@ -41,15 +52,6 @@ class LeftHeading(Heading):
|
|
|
41
52
|
def __rich_console__(self, console: Console, options: ConsoleOptions) -> RenderResult:
|
|
42
53
|
text = self.text
|
|
43
54
|
text.justify = "left" # Override justification
|
|
44
|
-
# if self.tag == "h1":
|
|
45
|
-
# from rich.panel import Panel
|
|
46
|
-
# from rich import box
|
|
47
|
-
# # Draw a border around h1s, but keep text left-aligned
|
|
48
|
-
# yield Panel(
|
|
49
|
-
# text,
|
|
50
|
-
# box=box.SQUARE,
|
|
51
|
-
# style="markdown.h1.border",
|
|
52
|
-
# )
|
|
53
55
|
if self.tag == "h2":
|
|
54
56
|
text.stylize(Style(bold=True, underline=False))
|
|
55
57
|
yield Rule(title=text, characters="-", style="markdown.h2.border", align="left")
|
|
@@ -68,6 +70,17 @@ class NoInsetMarkdown(Markdown):
|
|
|
68
70
|
}
|
|
69
71
|
|
|
70
72
|
|
|
73
|
+
class ThinkingMarkdown(Markdown):
|
|
74
|
+
"""Markdown for thinking content with grey-styled code blocks and left-justified headings."""
|
|
75
|
+
|
|
76
|
+
elements: ClassVar[dict[str, type[Any]]] = {
|
|
77
|
+
**Markdown.elements,
|
|
78
|
+
"fence": ThinkingCodeBlock,
|
|
79
|
+
"code_block": ThinkingCodeBlock,
|
|
80
|
+
"heading_open": LeftHeading,
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
|
|
71
84
|
class MarkdownStream:
|
|
72
85
|
"""Streaming markdown renderer that progressively displays content with a live updating window.
|
|
73
86
|
|
|
@@ -84,6 +97,7 @@ class MarkdownStream:
|
|
|
84
97
|
spinner: Spinner | None = None,
|
|
85
98
|
mark: str | None = None,
|
|
86
99
|
indent: int = 0,
|
|
100
|
+
markdown_class: Callable[..., Markdown] | None = None,
|
|
87
101
|
) -> None:
|
|
88
102
|
"""Initialize the markdown stream.
|
|
89
103
|
|
|
@@ -93,6 +107,7 @@ class MarkdownStream:
|
|
|
93
107
|
console (Console, optional): External console to use for rendering
|
|
94
108
|
mark (str | None, optional): Marker shown before the first non-empty line when indent >= 2
|
|
95
109
|
indent (int, optional): Number of spaces to indent all rendered lines on the left
|
|
110
|
+
markdown_class: Markdown class to use for rendering (defaults to NoInsetMarkdown)
|
|
96
111
|
"""
|
|
97
112
|
self.printed: list[str] = [] # Stores lines that have already been printed
|
|
98
113
|
|
|
@@ -118,6 +133,7 @@ class MarkdownStream:
|
|
|
118
133
|
self.spinner: Spinner | None = spinner
|
|
119
134
|
self.mark: str | None = mark
|
|
120
135
|
self.indent: int = max(indent, 0)
|
|
136
|
+
self.markdown_class: Callable[..., Markdown] = markdown_class or NoInsetMarkdown
|
|
121
137
|
|
|
122
138
|
@property
|
|
123
139
|
def _live_started(self) -> bool:
|
|
@@ -154,7 +170,7 @@ class MarkdownStream:
|
|
|
154
170
|
width=effective_width,
|
|
155
171
|
)
|
|
156
172
|
|
|
157
|
-
markdown =
|
|
173
|
+
markdown = self.markdown_class(text, **self.mdargs)
|
|
158
174
|
temp_console.print(markdown)
|
|
159
175
|
output = string_io.getvalue()
|
|
160
176
|
|
klaude_code/ui/rich/theme.py
CHANGED
|
@@ -14,12 +14,12 @@ class Palette:
|
|
|
14
14
|
blue: str
|
|
15
15
|
orange: str
|
|
16
16
|
magenta: str
|
|
17
|
-
grey_blue: str
|
|
18
17
|
grey1: str
|
|
19
18
|
grey2: str
|
|
20
19
|
grey3: str
|
|
21
20
|
grey_green: str
|
|
22
21
|
purple: str
|
|
22
|
+
lavender: str
|
|
23
23
|
diff_add: str
|
|
24
24
|
diff_remove: str
|
|
25
25
|
code_theme: str
|
|
@@ -31,15 +31,15 @@ LIGHT_PALETTE = Palette(
|
|
|
31
31
|
yellow="yellow",
|
|
32
32
|
green="spring_green4",
|
|
33
33
|
cyan="cyan",
|
|
34
|
-
blue="#
|
|
34
|
+
blue="#3078C5",
|
|
35
35
|
orange="#d77757",
|
|
36
36
|
magenta="magenta",
|
|
37
|
-
grey_blue="steel_blue",
|
|
38
37
|
grey1="#667e90",
|
|
39
38
|
grey2="#93a4b1",
|
|
40
39
|
grey3="#c4ced4",
|
|
41
|
-
grey_green="#
|
|
40
|
+
grey_green="#96a096",
|
|
42
41
|
purple="slate_blue3",
|
|
42
|
+
lavender="steel_blue",
|
|
43
43
|
diff_add="#2e5a32 on #e8f5e9",
|
|
44
44
|
diff_remove="#5a2e32 on #ffebee",
|
|
45
45
|
code_theme="ansi_light",
|
|
@@ -54,12 +54,12 @@ DARK_PALETTE = Palette(
|
|
|
54
54
|
blue="deep_sky_blue1",
|
|
55
55
|
orange="#e6704e",
|
|
56
56
|
magenta="magenta",
|
|
57
|
-
grey_blue="steel_blue",
|
|
58
57
|
grey1="#99aabb",
|
|
59
58
|
grey2="#778899",
|
|
60
59
|
grey3="#646464",
|
|
61
60
|
grey_green="#6d8672",
|
|
62
61
|
purple="#afbafe",
|
|
62
|
+
lavender="#9898b8",
|
|
63
63
|
diff_add="#c8e6c9 on #2e4a32",
|
|
64
64
|
diff_remove="#ffcdd2 on #4a2e32",
|
|
65
65
|
code_theme="ansi_dark",
|
|
@@ -107,6 +107,7 @@ class ThemeKey(str, Enum):
|
|
|
107
107
|
TOOL_MARK = "tool.mark"
|
|
108
108
|
TOOL_APPROVED = "tool.approved"
|
|
109
109
|
TOOL_REJECTED = "tool.rejected"
|
|
110
|
+
TOOL_TIMEOUT = "tool.timeout"
|
|
110
111
|
# THINKING
|
|
111
112
|
THINKING = "thinking"
|
|
112
113
|
THINKING_BOLD = "thinking.bold"
|
|
@@ -174,9 +175,9 @@ def get_theme(theme: str | None = None) -> Themes:
|
|
|
174
175
|
ThemeKey.USER_INPUT_AT_PATTERN.value: palette.purple,
|
|
175
176
|
ThemeKey.USER_INPUT_SLASH_COMMAND.value: "bold reverse " + palette.blue,
|
|
176
177
|
# METADATA
|
|
177
|
-
ThemeKey.METADATA.value: palette.
|
|
178
|
-
ThemeKey.METADATA_DIM.value: "dim " + palette.
|
|
179
|
-
ThemeKey.METADATA_BOLD.value: "bold " + palette.
|
|
178
|
+
ThemeKey.METADATA.value: palette.lavender,
|
|
179
|
+
ThemeKey.METADATA_DIM.value: "dim " + palette.lavender,
|
|
180
|
+
ThemeKey.METADATA_BOLD.value: "bold " + palette.lavender,
|
|
180
181
|
# SPINNER_STATUS
|
|
181
182
|
ThemeKey.SPINNER_STATUS.value: palette.blue,
|
|
182
183
|
ThemeKey.SPINNER_STATUS_TEXT.value: palette.blue,
|
|
@@ -196,6 +197,7 @@ def get_theme(theme: str | None = None) -> Themes:
|
|
|
196
197
|
ThemeKey.TOOL_MARK.value: "bold",
|
|
197
198
|
ThemeKey.TOOL_APPROVED.value: palette.green + " bold reverse",
|
|
198
199
|
ThemeKey.TOOL_REJECTED.value: palette.red + " bold reverse",
|
|
200
|
+
ThemeKey.TOOL_TIMEOUT.value: palette.yellow,
|
|
199
201
|
# THINKING
|
|
200
202
|
ThemeKey.THINKING.value: "italic " + palette.grey2,
|
|
201
203
|
ThemeKey.THINKING_BOLD.value: "bold italic " + palette.grey1,
|
|
@@ -232,7 +234,7 @@ def get_theme(theme: str | None = None) -> Themes:
|
|
|
232
234
|
markdown_theme=Theme(
|
|
233
235
|
styles={
|
|
234
236
|
"markdown.code": palette.purple,
|
|
235
|
-
"markdown.code.
|
|
237
|
+
"markdown.code.block": "on " + palette.text_background,
|
|
236
238
|
"markdown.h1": "bold reverse",
|
|
237
239
|
"markdown.h1.border": palette.grey3,
|
|
238
240
|
"markdown.h2.border": palette.grey3,
|
|
@@ -245,8 +247,7 @@ def get_theme(theme: str | None = None) -> Themes:
|
|
|
245
247
|
),
|
|
246
248
|
thinking_markdown_theme=Theme(
|
|
247
249
|
styles={
|
|
248
|
-
"markdown.code": palette.grey1 + " on " + palette.text_background,
|
|
249
|
-
"markdown.code.panel": palette.grey3,
|
|
250
|
+
"markdown.code": palette.grey1 + " italic on " + palette.text_background,
|
|
250
251
|
"markdown.h1": "bold reverse",
|
|
251
252
|
"markdown.h1.border": palette.grey3,
|
|
252
253
|
"markdown.h2.border": palette.grey3,
|
|
@@ -265,7 +266,6 @@ def get_theme(theme: str | None = None) -> Themes:
|
|
|
265
266
|
Style(color=palette.blue),
|
|
266
267
|
Style(color=palette.purple),
|
|
267
268
|
Style(color=palette.orange),
|
|
268
|
-
Style(color=palette.grey_blue),
|
|
269
269
|
Style(color=palette.red),
|
|
270
270
|
Style(color=palette.grey1),
|
|
271
271
|
Style(color=palette.yellow),
|
|
@@ -29,7 +29,7 @@ klaude_code/command/registry.py,sha256=Vy2WL1M35LL3aLkidXa2QGgGBFBKHQe_S93TZcH55
|
|
|
29
29
|
klaude_code/command/release_notes_cmd.py,sha256=lDeAjuMDOSUISM0yYKZKbkjrYvFmvA5_fylkalTPaBU,2707
|
|
30
30
|
klaude_code/command/status_cmd.py,sha256=F7XgfivBm80kJEsCgRHGXWOALAT_Y2QyLQ38ooc_ZSE,5393
|
|
31
31
|
klaude_code/command/terminal_setup_cmd.py,sha256=iSYGZlflj_i-7i-9FhfhtbyyIe3UNkhPeehZezi-ULM,10944
|
|
32
|
-
klaude_code/command/thinking_cmd.py,sha256=
|
|
32
|
+
klaude_code/command/thinking_cmd.py,sha256=pvCxyfDuF1aWJuYaRkVkDmuc0JkJUGBHJR2gNHt8PMQ,7997
|
|
33
33
|
klaude_code/config/__init__.py,sha256=Qrqvi8nizkj6N77h2vDj0r4rbgCiqxvz2HLBPFuWulA,120
|
|
34
34
|
klaude_code/config/config.py,sha256=2tSf6x88vuPfMMWcKlckXPoEjnxzFCtw2g_gbDjzK90,7268
|
|
35
35
|
klaude_code/config/list_model.py,sha256=Uthp0nHaENBgD6l_a6wG0RFkRHQhLvIyjHPsP55Kazw,8010
|
|
@@ -104,7 +104,7 @@ klaude_code/llm/anthropic/input.py,sha256=qPo4nmhnhSfLqef4UUVoIz8EjoXTxvlsrfsc_6
|
|
|
104
104
|
klaude_code/llm/client.py,sha256=FbFnzLUAKM61goiYNdKi8-D4rBfu_ksaxjJtmJn0w_4,960
|
|
105
105
|
klaude_code/llm/codex/__init__.py,sha256=8vN2j2ezWB_UVpfqQ8ooStsBeLL5SY4SUMXOXdWiMaI,132
|
|
106
106
|
klaude_code/llm/codex/client.py,sha256=0BAOiLAdk2PxBEYuC_TGOs4_h6yfNZr1YWuf1lzkBxM,5329
|
|
107
|
-
klaude_code/llm/input_common.py,sha256
|
|
107
|
+
klaude_code/llm/input_common.py,sha256=NxiYlhGRFntiLiKm5sKLCF0xGYW6DwcyvIhj6KAZoeU,8533
|
|
108
108
|
klaude_code/llm/openai_compatible/__init__.py,sha256=ACGpnki7k53mMcCl591aw99pm9jZOZk0ghr7atOfNps,81
|
|
109
109
|
klaude_code/llm/openai_compatible/client.py,sha256=DD1tnVqPIicmlG4tK0dlYgLkY_7vaZL8OvqYNRK6fu0,7846
|
|
110
110
|
klaude_code/llm/openai_compatible/input.py,sha256=rtWVjpwb9tLrinucezmncQXet8MerUxE5Gxc32sfDr4,3750
|
|
@@ -132,7 +132,7 @@ klaude_code/session/__init__.py,sha256=oXcDA5w-gJCbzmlF8yuWy3ezIW9DgFBNUs-gJHUJ-
|
|
|
132
132
|
klaude_code/session/export.py,sha256=yoRvIfEehjwHL9qNNd6kJWhXLdXTsQlpf8KCoR_tjkI,26512
|
|
133
133
|
klaude_code/session/selector.py,sha256=gijwWQkSV20XYP3Fxr27mFXuqP4ChY2DQm_YuBOTQKw,2888
|
|
134
134
|
klaude_code/session/session.py,sha256=w9ei9kkgT7-C4hlToQm0Cd35HTTOSPYkIGnrtaoJg6Q,21386
|
|
135
|
-
klaude_code/session/templates/export_session.html,sha256=
|
|
135
|
+
klaude_code/session/templates/export_session.html,sha256=BKFn1_EHg0vsF0g2J0sWoe0efF6eNk9loaPYEG8p3GQ,47705
|
|
136
136
|
klaude_code/trace/__init__.py,sha256=cETWJZZJaJ8_kA5Uki0om5n-ZpBxO9ph6YGYsJDXOEk,234
|
|
137
137
|
klaude_code/trace/log.py,sha256=0H_RqkytSpt6AAIFDg-MV_8vA9zsR9BB1UqT6moTTTg,9134
|
|
138
138
|
klaude_code/ui/__init__.py,sha256=XuEQsFUkJet8HI04cRmNLwnHOUqaPCRy4hF7PJnIfCY,2737
|
|
@@ -149,28 +149,28 @@ klaude_code/ui/modes/repl/__init__.py,sha256=35a6SUiL1SDi2i43X2VjHQw97rR7yhbLBzk
|
|
|
149
149
|
klaude_code/ui/modes/repl/clipboard.py,sha256=ZCpk7kRSXGhh0Q_BWtUUuSYT7ZOqRjAoRcg9T9n48Wo,5137
|
|
150
150
|
klaude_code/ui/modes/repl/completers.py,sha256=RyxvbOwVXTa4PTl1thVz6YbBhXhCZa7ZX87eiGRHGp4,18224
|
|
151
151
|
klaude_code/ui/modes/repl/display.py,sha256=0u4ISeOoYjynF7InYyV-PMOZqP44QBbjYOLOL18V0c0,2245
|
|
152
|
-
klaude_code/ui/modes/repl/event_handler.py,sha256
|
|
152
|
+
klaude_code/ui/modes/repl/event_handler.py,sha256=j24Q-ygfI2RHuYj2Atg_1vrzW7fT6lx-jww11Uzs25g,21220
|
|
153
153
|
klaude_code/ui/modes/repl/input_prompt_toolkit.py,sha256=EAIAtcL9EHVPmVK6oOHg0xCeZ0IOnG5S5KsaL85OHOk,6368
|
|
154
154
|
klaude_code/ui/modes/repl/key_bindings.py,sha256=Fxz9Ey2SnOHvfleMeSYVduxuofY0Yo-97hMRs-OMe-o,7800
|
|
155
|
-
klaude_code/ui/modes/repl/renderer.py,sha256=
|
|
155
|
+
klaude_code/ui/modes/repl/renderer.py,sha256=M0Fhj_mQXyjHnKDzrmZ0mnPk7L6IFIU4wCgHSsffmAQ,11406
|
|
156
156
|
klaude_code/ui/renderers/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
157
157
|
klaude_code/ui/renderers/assistant.py,sha256=Dxy6v4pX28RyWhnrjBteY8_NvDIi_jQa-j0mWt-eqWY,569
|
|
158
158
|
klaude_code/ui/renderers/common.py,sha256=TPH7LCbeJGqB8ArTsVitqJHEyOxHU6nwnRtvF04nLJ4,184
|
|
159
159
|
klaude_code/ui/renderers/developer.py,sha256=fE-9LRzVLiKnK3ctFcuDDP_eehohhsgPCH_tYaOp-xs,6378
|
|
160
160
|
klaude_code/ui/renderers/diffs.py,sha256=iPQxxZW1JGPwtTdCKMEkDlNb5trLm9tdWjfMRmtj6yQ,7616
|
|
161
161
|
klaude_code/ui/renderers/errors.py,sha256=c_fbnoNOnvuI3Bb24IujwV8Mpes-qWS_xCWfAcBvg6A,517
|
|
162
|
-
klaude_code/ui/renderers/metadata.py,sha256=
|
|
162
|
+
klaude_code/ui/renderers/metadata.py,sha256=gnnIEs7iFiWNCADKa7N9FtDxvVZKtVo-6JuT2I9sIhA,7760
|
|
163
163
|
klaude_code/ui/renderers/sub_agent.py,sha256=3cyn95pu4IniOJyWW4vfQ-X72iLufQ3LT9CkAQMuF4k,2686
|
|
164
|
-
klaude_code/ui/renderers/thinking.py,sha256=
|
|
165
|
-
klaude_code/ui/renderers/tools.py,sha256=
|
|
164
|
+
klaude_code/ui/renderers/thinking.py,sha256=rYc7KttyEW7r3133dFLofpiQCYH-NiZolexYo-N8Vfs,1181
|
|
165
|
+
klaude_code/ui/renderers/tools.py,sha256=d-8udsM-81P6rwQhJgmN_J93Kj8KVvrUBbcH86PmTRc,21619
|
|
166
166
|
klaude_code/ui/renderers/user_input.py,sha256=rDdOYvbgJ6oePQAtyTCK-KhARfLKytpTZboZ-cFIuJQ,2603
|
|
167
167
|
klaude_code/ui/rich/__init__.py,sha256=olvMm2SteyKioOqUJbEoav2TsDr_mtKqkSaifNumjwc,27
|
|
168
168
|
klaude_code/ui/rich/live.py,sha256=Uid0QAZG7mHb4KrCF8p9c9n1nHLHzW75xSqcLZ4bLWY,2098
|
|
169
|
-
klaude_code/ui/rich/markdown.py,sha256=
|
|
169
|
+
klaude_code/ui/rich/markdown.py,sha256=k5Kx5SSoSMnVW-35dZw6Yp26ahPErDYVpKPI6wpXP8c,12347
|
|
170
170
|
klaude_code/ui/rich/quote.py,sha256=tZcxN73SfDBHF_qk0Jkh9gWBqPBn8VLp9RF36YRdKEM,1123
|
|
171
171
|
klaude_code/ui/rich/searchable_text.py,sha256=DCVZgEFv7_ergAvT2v7XrfQAUXUzhmAwuVAchlIx8RY,2448
|
|
172
172
|
klaude_code/ui/rich/status.py,sha256=r5KmymTKo-FsOVBJxp8orhqFT8GP8Mf1DHkw1icnuOA,8522
|
|
173
|
-
klaude_code/ui/rich/theme.py,sha256=
|
|
173
|
+
klaude_code/ui/rich/theme.py,sha256=yMGWoVzG9leHB3eR4ufFzW2nAhXOtiYEwwn0kvCtr4E,10140
|
|
174
174
|
klaude_code/ui/terminal/__init__.py,sha256=GIMnsEcIAGT_vBHvTlWEdyNmAEpruyscUA6M_j3GQZU,1412
|
|
175
175
|
klaude_code/ui/terminal/color.py,sha256=M-i09DVlLAhAyhQjfeAi7OipoGi1p_OVkaZxeRfykY0,7135
|
|
176
176
|
klaude_code/ui/terminal/control.py,sha256=6SGNwxorP3jMW9xqnZy2BC0OsJd4DSrS13O3t6YlZzs,4916
|
|
@@ -180,7 +180,7 @@ klaude_code/ui/utils/__init__.py,sha256=YEsCLjbCPaPza-UXTPUMTJTrc9BmNBUP5CbFWlsh
|
|
|
180
180
|
klaude_code/ui/utils/common.py,sha256=UCQMun23l-EREr3xkl-Bjx67yfi9ctRTw2gcGPsOM2c,2881
|
|
181
181
|
klaude_code/ui/utils/debouncer.py,sha256=x8AYxf48Xd6tabBvH8cVl1bIV8FzyeDo3HswDjtNfwU,1266
|
|
182
182
|
klaude_code/version.py,sha256=x2OeiACPdzS87EWtaSi_UP13htm81Uq7mlV3kFy5jko,4815
|
|
183
|
-
klaude_code-1.2.
|
|
184
|
-
klaude_code-1.2.
|
|
185
|
-
klaude_code-1.2.
|
|
186
|
-
klaude_code-1.2.
|
|
183
|
+
klaude_code-1.2.15.dist-info/WHEEL,sha256=eh7sammvW2TypMMMGKgsM83HyA_3qQ5Lgg3ynoecH3M,79
|
|
184
|
+
klaude_code-1.2.15.dist-info/entry_points.txt,sha256=7CWKjolvs6dZiYHpelhA_FRJ-sVDh43eu3iWuOhKc_w,53
|
|
185
|
+
klaude_code-1.2.15.dist-info/METADATA,sha256=r1bX2TVm7kMRX4v3YEHPbhn7P954cykmgxHvQFZG2o4,5067
|
|
186
|
+
klaude_code-1.2.15.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|