kash-shell 0.3.26__py3-none-any.whl → 0.3.28__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.
kash/actions/__init__.py CHANGED
@@ -1,4 +1,5 @@
1
1
  from dataclasses import dataclass
2
+ from importlib import metadata
2
3
  from pathlib import Path
3
4
 
4
5
  from strif import AtomicVar
@@ -15,9 +16,11 @@ import_and_register(__package__, Path(__file__).parent, ["core", "meta"])
15
16
 
16
17
  @dataclass(frozen=True)
17
18
  class Kit:
18
- name: str
19
+ module_name: str
20
+ distribution_name: str
19
21
  full_module_name: str
20
22
  path: Path | None
23
+ version: str | None = None
21
24
 
22
25
 
23
26
  _kits: AtomicVar[dict[str, Kit]] = AtomicVar(initial_value={})
@@ -30,6 +33,44 @@ def get_loaded_kits() -> dict[str, Kit]:
30
33
  return _kits.copy()
31
34
 
32
35
 
36
+ def get_kit_distribution_name(module_name: str) -> str | None:
37
+ """
38
+ Guess the distribution name for a kit module using naming conventions.
39
+ Assumes kits follow patterns like:
40
+ - kash.kits.example_kit -> kash-example-kit
41
+ """
42
+ if not module_name.startswith("kash.kits."):
43
+ return None
44
+
45
+ kit_name = module_name.removeprefix("kash.kits.")
46
+
47
+ # Try common naming patterns
48
+ candidates = [
49
+ f"kash-{kit_name}",
50
+ f"kash-{kit_name.replace('_', '-')}",
51
+ ]
52
+
53
+ for candidate in candidates:
54
+ try:
55
+ metadata.version(candidate)
56
+ return candidate
57
+ except metadata.PackageNotFoundError:
58
+ continue
59
+
60
+ return None
61
+
62
+
63
+ def get_distribution_version(module_name: str) -> str | None:
64
+ """
65
+ Get the version of a module that can be used with `metadata.version()`.
66
+ """
67
+ try:
68
+ dist_name = get_kit_distribution_name(module_name)
69
+ return metadata.version(dist_name) if dist_name else None
70
+ except Exception:
71
+ return None
72
+
73
+
33
74
  def load_kits() -> dict[str, Kit]:
34
75
  """
35
76
  Import all kits (modules within `kash.kits`) by inspecting the namespace.
@@ -38,11 +79,15 @@ def load_kits() -> dict[str, Kit]:
38
79
  new_kits = {}
39
80
  try:
40
81
  imported = import_namespace_modules(kits_namespace)
41
- for name, module in imported.items():
42
- new_kits[name] = Kit(
43
- name,
44
- module.__name__,
45
- Path(module.__file__) if module.__file__ else None,
82
+ for module_name, module in imported.items():
83
+ dist_name = get_kit_distribution_name(module.__name__) or module.__name__
84
+
85
+ new_kits[module_name] = Kit(
86
+ module_name=module_name,
87
+ distribution_name=dist_name,
88
+ full_module_name=module.__name__,
89
+ path=Path(module.__file__) if module.__file__ else None,
90
+ version=metadata.version(dist_name),
46
91
  )
47
92
  except ImportError:
48
93
  log.info("No kits found in namespace `%s`", kits_namespace)
@@ -22,7 +22,7 @@ def minify_html(item: Item) -> Item:
22
22
  The terser minification seems a bit slower but more robust than
23
23
  [minify-html](https://github.com/wilsonzlin/minify-html).
24
24
  """
25
- from minify_tw_html import minify_tw_html
25
+ from tminify.main import tminify
26
26
 
27
27
  if not item.store_path:
28
28
  raise InvalidInput(f"Missing store path: {item}")
@@ -33,7 +33,7 @@ def minify_html(item: Item) -> Item:
33
33
  output_item = item.derived_copy(format=Format.html, body=None)
34
34
  output_path = ws.target_path_for(output_item)
35
35
 
36
- minify_tw_html(input_path, output_path)
36
+ tminify(input_path, output_path)
37
37
 
38
38
  output_item.body = output_path.read_text()
39
39
  output_item.external_path = str(output_path) # Indicate item is already saved.
@@ -39,7 +39,7 @@ def version() -> None:
39
39
  """
40
40
  Show the version of kash.
41
41
  """
42
- cprint(get_full_version_name())
42
+ cprint(get_full_version_name(with_kits=True))
43
43
 
44
44
 
45
45
  @kash_command
@@ -205,7 +205,9 @@ def kits() -> None:
205
205
  cprint("Currently imported kits:")
206
206
  for kit in get_loaded_kits().values():
207
207
  cprint(
208
- format_name_and_value(f"{kit.name} kit", str(kit.path or ""), text_wrap=Wrap.NONE)
208
+ format_name_and_value(
209
+ f"{kit.distribution_name} kit", str(kit.path or ""), text_wrap=Wrap.NONE
210
+ )
209
211
  )
210
212
 
211
213
 
@@ -31,4 +31,4 @@ def welcome() -> None:
31
31
  )
32
32
  )
33
33
  cprint(Panel(Markdown(help_topics.warning), box=SQUARE, border_style=COLOR_HINT))
34
- cprint("%s", get_full_version_name())
34
+ cprint("%s", get_full_version_name(with_kits=True))
kash/config/colors.py CHANGED
@@ -145,6 +145,7 @@ web_light_translucent = SimpleNamespace(
145
145
  text=hsl_to_hex("hsl(188, 39%, 11%)"),
146
146
  code=hsl_to_hex("hsl(44, 38%, 23%)"),
147
147
  border=hsl_to_hex("hsl(188, 8%, 50%)"),
148
+ border_hairline=hsl_to_hex("hsl(188, 2%, 34%)"),
148
149
  border_hint=hsl_to_hex("hsla(188, 8%, 72%, 0.3)"),
149
150
  border_accent=hsl_to_hex("hsla(305, 18%, 65%, 0.85)"),
150
151
  hover=hsl_to_hex("hsl(188, 12%, 84%)"),
@@ -180,6 +181,7 @@ web_dark_translucent = SimpleNamespace(
180
181
  text=hsl_to_hex("hsl(188, 10%, 90%)"),
181
182
  code=hsl_to_hex("hsl(44, 38%, 72%)"),
182
183
  border=hsl_to_hex("hsl(188, 8%, 25%)"),
184
+ border_hairline=hsl_to_hex("hsl(188, 2%, 80%)"),
183
185
  border_hint=hsl_to_hex("hsla(188, 8%, 35%, 0.3)"),
184
186
  border_accent=hsl_to_hex("hsla(305, 30%, 55%, 0.85)"),
185
187
  hover=hsl_to_hex("hsl(188, 12%, 35%)"),
kash/config/logger.py CHANGED
@@ -170,6 +170,7 @@ def reset_rich_logging(
170
170
  the `.log` extension. If `log_path` is provided, it will be used to infer
171
171
  the log root and name.
172
172
  """
173
+ _init_rich_logging()
173
174
  if log_path:
174
175
  if not log_path.parent.exists():
175
176
  log_path.parent.mkdir(parents=True, exist_ok=True)
@@ -206,6 +207,9 @@ def reload_rich_logging_setup():
206
207
 
207
208
  @cache
208
209
  def _init_rich_logging():
210
+ """
211
+ One-time idempotent setup of rich logging.
212
+ """
209
213
  rich.reconfigure(theme=get_theme(), highlighter=get_highlighter())
210
214
 
211
215
  logging.setLoggerClass(CustomLogger)
@@ -2,20 +2,18 @@ from __future__ import annotations
2
2
 
3
3
  import atexit
4
4
  import threading
5
- import time
6
5
  from collections.abc import Generator
7
6
  from contextlib import contextmanager
8
7
  from dataclasses import dataclass, field
9
8
 
10
- from rich.console import Console, RenderableType
9
+ from rich.console import Console, Group, RenderableType
11
10
  from rich.live import Live
12
11
  from rich.spinner import Spinner
13
12
  from rich.text import Text
14
- from rich.console import Group
15
13
  from strif import AtomicVar
16
14
 
17
15
  from kash.config.logger import get_console
18
- from kash.config.text_styles import SPINNER, COLOR_SPINNER
16
+ from kash.config.text_styles import COLOR_SPINNER, SPINNER
19
17
 
20
18
 
21
19
  @dataclass
@@ -8,7 +8,6 @@ from typing import TYPE_CHECKING
8
8
 
9
9
  from mcp.server.sse import SseServerTransport
10
10
  from prettyfmt import fmt_path
11
- from sse_starlette.sse import AppStatus
12
11
  from starlette.applications import Starlette
13
12
  from starlette.routing import Mount, Route
14
13
 
@@ -72,10 +71,6 @@ class MCPServerSSE:
72
71
  def _setup_server(self):
73
72
  import uvicorn
74
73
 
75
- # Reset AppStatus.should_exit_event to None to ensure it's created
76
- # in the correct event loop when needed.
77
- AppStatus.should_exit_event = None
78
-
79
74
  port = global_settings().mcp_server_port
80
75
 
81
76
  # Check if the port is available.
kash/model/items_model.py CHANGED
@@ -263,7 +263,7 @@ class Item:
263
263
  thumbnail_url: Url | None = None
264
264
 
265
265
  # Optional additional metadata.
266
- extra: dict | None = None
266
+ extra: dict[str, Any] | None = None
267
267
 
268
268
  # Optional execution context. Useful for letting functions that take only an Item
269
269
  # arg get access to context.
kash/shell/shell_main.py CHANGED
@@ -1,5 +1,5 @@
1
1
  """
2
- Welcome to kash! Main way to run the kash shell.
2
+ Welcome to Kash! This command is the main way to run the kash shell.
3
3
 
4
4
  Usually this is used to start the kash interactively but you can also pass a single
5
5
  command to run non-interactively.
@@ -13,16 +13,16 @@ More information at: github.com/jlevy/kash
13
13
  import argparse
14
14
  import threading
15
15
 
16
- import xonsh.main
17
- from clideps.utils.readable_argparse import ReadableColorFormatter
18
16
  from strif import quote_if_needed
19
17
 
18
+ from kash.config.logger import get_console, get_logger
20
19
  from kash.config.setup import kash_setup
21
20
  from kash.shell.version import get_full_version_name, get_version
22
- from kash.xonsh_custom.custom_shell import install_to_xonshrc, start_shell
23
21
 
24
22
  kash_setup(rich_logging=True) # Set up logging first.
25
23
 
24
+ log = get_logger(__name__)
25
+
26
26
 
27
27
  __version__ = get_version()
28
28
 
@@ -35,6 +35,10 @@ def run_plain_xonsh():
35
35
  xontrib only (in ~/.xonshrc), but the full customizations of prompts, tab
36
36
  completion, etc are not available.
37
37
  """
38
+ import xonsh.main
39
+
40
+ from kash.xonsh_custom.custom_shell import install_to_xonshrc
41
+
38
42
  install_to_xonshrc()
39
43
  xonsh.main.main()
40
44
 
@@ -42,25 +46,77 @@ def run_plain_xonsh():
42
46
  # Event to monitor loading.
43
47
  shell_ready_event = threading.Event()
44
48
 
49
+ imports_done_event = threading.Event()
50
+
45
51
 
46
52
  def run_shell(single_command: str | None = None):
47
53
  """
48
54
  Run the kash shell interactively or non-interactively with a single command.
49
55
  """
56
+ from kash.xonsh_custom.custom_shell import start_shell
57
+
50
58
  start_shell(single_command, shell_ready_event)
51
59
 
52
60
 
53
61
  def build_parser() -> argparse.ArgumentParser:
62
+ from clideps.utils.readable_argparse import ReadableColorFormatter
63
+
54
64
  parser = argparse.ArgumentParser(description=__doc__, formatter_class=ReadableColorFormatter)
55
65
 
56
- parser.add_argument("--version", action="version", version=get_full_version_name())
66
+ # Don't call get_full_version_name() here, as it's slow.
67
+ parser.add_argument("--version", action="store_true", help="show version and exit")
57
68
 
58
69
  return parser
59
70
 
60
71
 
72
+ def _import_packages():
73
+ try:
74
+ # Slowest packages:
75
+ import uvicorn.protocols # noqa: F401
76
+ import uvicorn.protocols.http.h11_impl # noqa: F401
77
+ import uvicorn.protocols.websockets.websockets_impl # noqa: F401
78
+ import xonsh.completers.init # noqa: F401
79
+ import xonsh.pyghooks # noqa: F401
80
+
81
+ import kash.actions # noqa: F401
82
+ import kash.local_server # noqa: F401
83
+ import kash.local_server.local_server # noqa: F401
84
+ import kash.mcp.mcp_server_sse # noqa: F401
85
+ except ImportError as e:
86
+ log.warning(f"Error pre-importing packages: {e}")
87
+
88
+ imports_done_event.set()
89
+
90
+
91
+ def import_with_status_if_slow(min_time: float = 1.0):
92
+ """
93
+ Not required, but imports can be remarkably slow the first time, so this shows a status message.
94
+ """
95
+
96
+ # Start imports in background thread
97
+ import_thread = threading.Thread(target=_import_packages, daemon=True)
98
+ import_thread.start()
99
+
100
+ # Wait for imports to complete, with a short timeout
101
+ if not imports_done_event.wait(timeout=min_time):
102
+ # If imports aren't done quickly, show status message
103
+ if get_console().is_terminal:
104
+ with get_console().status(
105
+ "Importing packages (this is a bit slow the first time) …", spinner="line"
106
+ ):
107
+ import_thread.join()
108
+ else:
109
+ import_thread.join()
110
+
111
+
61
112
  def main():
62
113
  parser = build_parser()
63
- _args, unknown = parser.parse_known_args()
114
+
115
+ args, unknown = parser.parse_known_args()
116
+
117
+ if args.version:
118
+ print(get_full_version_name(with_kits=True))
119
+ return
64
120
 
65
121
  # Join remaining arguments to pass as a single command to kash.
66
122
  # Use Python-style quoting only if needed for xonsh.
@@ -68,6 +124,8 @@ def main():
68
124
  if unknown:
69
125
  single_command = " ".join(quote_if_needed(arg) for arg in unknown)
70
126
 
127
+ import_with_status_if_slow()
128
+
71
129
  run_shell(single_command)
72
130
 
73
131
 
kash/shell/version.py CHANGED
@@ -28,8 +28,24 @@ def get_version_tag():
28
28
  return f"v{get_version()}"
29
29
 
30
30
 
31
- def get_full_version_name():
32
- return f"{PACKAGE_NAME} {get_version_tag()}"
31
+ def get_full_version_name(with_kits: bool = False):
32
+ """
33
+ Get the full version name, including the version number and any loaded kits.
34
+
35
+ If `with_kits` is True, will also import `kash.kits` packages and get those versions,
36
+ but be careful as this can be much slower due to imports!
37
+ """
38
+
39
+ version_items = [f"{PACKAGE_NAME} {get_version_tag()}"]
40
+ if with_kits:
41
+ from kash.actions import get_loaded_kits
42
+
43
+ kits = get_loaded_kits()
44
+ for kit in kits.values():
45
+ if kit.version:
46
+ version_items.append(f"{kit.distribution_name} v{kit.version}")
47
+
48
+ return ", ".join(version_items)
33
49
 
34
50
 
35
51
  if __name__ == "__main__":
@@ -22,15 +22,19 @@
22
22
  --font-size-large: 1.2rem;
23
23
  --font-size-normal: 1rem;
24
24
  --font-size-small: 0.95rem;
25
- --font-size-smaller: 0.85rem;
25
+ --font-size-smaller: 0.9rem;
26
+ --font-size-tiny: 0.85rem;
26
27
  --font-size-mono: 0.82rem;
27
28
  --font-size-mono-small: 0.75rem;
28
29
  --font-size-mono-tiny: 0.7rem;
29
30
 
31
+ --line-height-normal: 1.5;
32
+ --line-height-tight: 1.2;
33
+
30
34
  /* Both Source Sans 3 and PT Serif have small caps, so we use this instead of text-transform. */
31
35
  --caps-transform: none;
32
36
  --caps-caps-variant: all-small-caps;
33
- --caps-spacing: 0.025em;
37
+ --caps-spacing: 0.021em;
34
38
  /* Compensate for small caps (Source Sans small caps are quite small) */
35
39
  --caps-heading-size-multiplier: 1.42;
36
40
  --caps-heading-line-height: calc(1.2 / var(--caps-heading-size-multiplier));
@@ -107,7 +111,7 @@ html {
107
111
  body {
108
112
  font-family: var(--font-serif);
109
113
  color: var(--color-text);
110
- line-height: 1.5;
114
+ line-height: var(--line-height-normal);
111
115
  padding: 0; /* No padding so we can have full width elements. */
112
116
  margin: auto;
113
117
  background-color: var(--color-bg);
@@ -142,7 +146,7 @@ a:hover {
142
146
  }
143
147
 
144
148
  h1, h2, h3, h4, h5, h6 {
145
- line-height: 1.2;
149
+ line-height: var(--line-height-tight);
146
150
  }
147
151
 
148
152
  h1 {
@@ -196,7 +200,7 @@ h4+p, h5+p, h6+p {
196
200
  ul {
197
201
  list-style-type: none;
198
202
  margin-left: 1.8rem;
199
- margin-bottom: 1rem;
203
+ margin-bottom: 0.7rem;
200
204
  padding-left: 0;
201
205
  }
202
206
 
@@ -207,6 +211,7 @@ li {
207
211
  }
208
212
 
209
213
  li > p {
214
+ /* No extra padding for paragraphs inside list items. */
210
215
  margin-bottom: 0;
211
216
  }
212
217
 
@@ -229,10 +234,9 @@ ol > li {
229
234
  }
230
235
 
231
236
  blockquote {
232
- border-left: 2px solid var(--color-primary);
237
+ {# border-left: 1px solid var(--color-border-hairline); #}
233
238
  padding-left: 1rem;
234
- margin-left: 0;
235
- margin-right: 0;
239
+ margin: 1.5rem 4rem 1.5rem 1rem;
236
240
  }
237
241
 
238
242
  /* Inline code styling */
@@ -240,7 +244,6 @@ code {
240
244
  font-family: var(--font-mono);
241
245
  font-size: var(--font-size-mono);
242
246
  letter-spacing: -0.025em;
243
-
244
247
  transition: color 0.4s ease-in-out;
245
248
  }
246
249
  /* For code inside pre we style the pre tag */
@@ -619,12 +622,14 @@ sup {
619
622
 
620
623
  @media print {
621
624
  sup {
622
- font-size: 70% !important;
625
+ /* Using small-caps so this is a bit larger */
626
+ font-size: 110% !important;
623
627
  }
624
628
 
625
629
  /* Don't use stylized footnotes in print. */
626
630
  .footnote-ref a, .footnote {
627
631
  font-family: var(--font-serif);
632
+ font-variant-caps: all-small-caps !important;
628
633
  font-feature-settings: normal !important;
629
634
  background-color: transparent !important;
630
635
  color: var(--color-text) !important;
@@ -675,9 +680,9 @@ sup {
675
680
 
676
681
  @bottom-right {
677
682
  content: counter(page);
678
- font-family: var(--font-sans) !important;
683
+ font-family: var(--font-serif) !important;
679
684
  font-size: var(--font-size-small);
680
- color: var(--color-tertiary) !important;
685
+ color: var(--color-text) !important;
681
686
  margin: 0 0 0.2in 0 !important;
682
687
  }
683
688
  }
@@ -688,13 +693,25 @@ sup {
688
693
  --font-size-small: 1.0rem;
689
694
  --font-size-smaller: 0.9rem;
690
695
  --font-size-mono: 0.9rem;
696
+
697
+ /* Tighter line height for print readability */
698
+ --line-height-normal: 1.4;
699
+ --line-height-tight: 1.15;
691
700
  }
692
701
 
693
- body {
702
+ body {
694
703
  /* Remove body margin since @page handles it */
695
704
  margin: 0;
696
- /* Ensure good line height for print */
697
- line-height: 1.6;
705
+ }
706
+
707
+ /* Reduce spacing between block elements to match tighter line height */
708
+ p {
709
+ margin-top: 0.65rem;
710
+ margin-bottom: 0.65rem;
711
+ }
712
+
713
+ li {
714
+ margin-top: 0.6rem;
698
715
  }
699
716
 
700
717
  /* Enable hyphenation and justification for main text content only */
@@ -703,8 +720,6 @@ sup {
703
720
  text-align: justify;
704
721
  }
705
722
 
706
-
707
-
708
723
  .long-text {
709
724
  /* Remove shadows and borders that don't work well in print */
710
725
  box-shadow: none !important;
@@ -713,6 +728,15 @@ sup {
713
728
  padding: 0;
714
729
  }
715
730
 
731
+ /* Slightly darker sans-serif headings look better in print. */
732
+ .long-text h3 {
733
+ font-weight: 580;
734
+ }
735
+
736
+ .long-text h4 {
737
+ font-weight: 580;
738
+ }
739
+
716
740
  /* Ensure tables don't break layout in print */
717
741
  .table-container {
718
742
  position: static;
@@ -733,6 +757,15 @@ sup {
733
757
  pre {
734
758
  white-space: pre-wrap;
735
759
  word-wrap: break-word;
760
+ background-color: transparent !important;
761
+ border: none !important;
762
+ font-weight: normal !important;
763
+ }
764
+
765
+ code {
766
+ background-color: transparent !important;
767
+ border: none !important;
768
+ font-weight: normal !important;
736
769
  }
737
770
 
738
771
  /* Hide interactive elements that don't work in print */
@@ -760,11 +793,6 @@ sup {
760
793
  widows: 3; /* Minimum lines at top of page */
761
794
  }
762
795
 
763
- /* Keep list items together when reasonable */
764
- li {
765
- break-inside: avoid-page;
766
- page-break-inside: avoid; /* Fallback for older browsers */
767
- }
768
796
 
769
797
  /* Hide doc metadata details in print (for now) */
770
798
  details.metadata {
@@ -10,6 +10,38 @@
10
10
 
11
11
  {% block title %}<title>{{ title }}</title>{% endblock title %}
12
12
 
13
+ {% block social_meta %}
14
+ {% if social_meta %}
15
+ <!-- Open Graph meta tags -->
16
+ <meta property="og:title" content="{{ social_meta.title or title }}" />
17
+ {% if social_meta.description %}
18
+ <meta property="og:description" content="{{ social_meta.description }}" />
19
+ {% endif %}
20
+ {% if social_meta.image %}
21
+ <meta property="og:image" content="{{ social_meta.image }}" />
22
+ {% endif %}
23
+ {% if social_meta.url %}
24
+ <meta property="og:url" content="{{ social_meta.url }}" />
25
+ {% endif %}
26
+ <meta property="og:type" content="{{ social_meta.type or 'website' }}" />
27
+ {% if social_meta.site_name %}
28
+ <meta property="og:site_name" content="{{ social_meta.site_name }}" />
29
+ {% endif %}
30
+ <!-- Twitter Card meta tags -->
31
+ <meta name="twitter:card" content="summary_large_image" />
32
+ <meta name="twitter:title" content="{{ social_meta.title or title }}" />
33
+ {% if social_meta.description %}
34
+ <meta name="twitter:description" content="{{ social_meta.description }}" />
35
+ {% endif %}
36
+ {% if social_meta.image %}
37
+ <meta name="twitter:image" content="{{ social_meta.image }}" />
38
+ {% endif %}
39
+ {% if social_meta.twitter_handle %}
40
+ <meta name="twitter:site" content="@{{ social_meta.twitter_handle }}" />
41
+ {% endif %}
42
+ {% endif %}
43
+ {% endblock social_meta %}
44
+
13
45
  {% block dark_mode_script %}
14
46
  <script>
15
47
  // Set theme before body renders to prevent flash of unstyled content
@@ -91,7 +91,7 @@
91
91
 
92
92
  .toc-title {
93
93
  font-weight: 550;
94
- font-size: calc(var(--font-size-small) * var(--caps-heading-size-multiplier));
94
+ font-size: calc(var(--font-size-smaller) * var(--caps-heading-size-multiplier));
95
95
  line-height: var(--caps-heading-line-height);
96
96
  text-transform: var(--caps-transform);
97
97
  font-variant-caps: var(--caps-caps-variant);
@@ -105,7 +105,7 @@
105
105
  list-style: none;
106
106
  margin: 0.5rem 0 0 0;
107
107
  padding: 0;
108
- font-size: var(--font-size-small);
108
+ font-size: var(--font-size-smaller);
109
109
  line-height: 1.2;
110
110
  }
111
111
 
@@ -276,6 +276,15 @@ body.toc-open {
276
276
  .toc-link.active {
277
277
  color: var(--color-text);
278
278
  }
279
+
280
+ /* Slightly larger TOC font size on mobile */
281
+ .toc-title {
282
+ font-size: calc(var(--font-size-small) * var(--caps-heading-size-multiplier));
283
+ }
284
+
285
+ .toc-list {
286
+ font-size: var(--font-size-small);
287
+ }
279
288
 
280
289
  .toc-container.mobile-visible {
281
290
  /* Visible state */
@@ -69,6 +69,7 @@
69
69
  font-family: var(--font-sans);
70
70
  font-feature-settings: var(--font-features-sans);
71
71
  font-size: var(--font-size-small);
72
+ font-weight: 400;
72
73
  line-height: 1.4;
73
74
  padding: var(--tooltip-padding);
74
75
  border-radius: 0; /* Square corners for all tooltips */
@@ -23,15 +23,12 @@ from xonsh.shells.ptk_shell.formatter import PTKPromptFormatter
23
23
  from xonsh.xontribs import xontribs_load
24
24
 
25
25
  import kash.config.suppress_warnings # noqa: F401 # usort:skip
26
-
27
- # Keeping initial imports/deps minimal.
28
- from kash.config.unified_live import get_unified_live
29
26
  from kash.config import colors
30
- from kash.config.unified_live import get_unified_live
31
27
  from kash.config.lazy_imports import import_start_time # usort:skip
32
28
  from kash.config.logger import get_log_settings, get_logger
33
29
  from kash.config.settings import APP_NAME, find_rcfiles
34
30
  from kash.config.text_styles import STYLE_ASSISTANCE, STYLE_HINT
31
+ from kash.config.unified_live import get_unified_live
35
32
  from kash.help.assistant import AssistanceType
36
33
  from kash.shell.output.shell_output import cprint
37
34
  from kash.shell.ui.shell_syntax import is_assist_request_str
@@ -130,20 +130,14 @@ def log_command_action_info():
130
130
  kits = get_loaded_kits()
131
131
  action_count = len(get_all_action_classes())
132
132
  command_count = len(get_all_commands())
133
- cprint(
134
- Text.assemble(
135
- Text("Kits loaded: "),
136
- Text(
137
- f"{', '.join(kits.keys()) if kits else 'none'}", style=COLOR_VALUE if kits else ""
138
- ),
139
- )
140
- )
133
+ kits_list = ["kash-shell"] + list(k.distribution_name for k in kits.values())
141
134
  cprint(
142
135
  Text.assemble(
143
136
  Text(f"{command_count} commands", style=COLOR_VALUE),
144
137
  Text(" and "),
145
138
  Text(f"{action_count} actions", style=COLOR_VALUE),
146
- Text(" loaded."),
139
+ Text(" loaded from "),
140
+ Text(f"{', '.join(kits_list)}", style=COLOR_VALUE if kits_list else ""),
147
141
  )
148
142
  )
149
143
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: kash-shell
3
- Version: 0.3.26
3
+ Version: 0.3.28
4
4
  Summary: The knowledge agent shell (core)
5
5
  Project-URL: Repository, https://github.com/jlevy/kash-shell
6
6
  Author-email: Joshua Levy <joshua@cal.berkeley.edu>
@@ -29,7 +29,7 @@ Requires-Dist: deepgram-sdk>=3.10.1
29
29
  Requires-Dist: dunamai>=1.23.0
30
30
  Requires-Dist: fastapi>=0.115.11
31
31
  Requires-Dist: flowmark>=0.5.2
32
- Requires-Dist: frontmatter-format>=0.2.1
32
+ Requires-Dist: frontmatter-format>=0.2.2
33
33
  Requires-Dist: funlog>=0.2.0
34
34
  Requires-Dist: httpx[brotli]>=0.28.1
35
35
  Requires-Dist: humanfriendly>=10.0
@@ -37,11 +37,10 @@ Requires-Dist: inquirerpy>=0.3.4
37
37
  Requires-Dist: jinja2>=3.1.6
38
38
  Requires-Dist: justext>=3.0.2
39
39
  Requires-Dist: lazyasd>=0.1.4
40
- Requires-Dist: litellm>=1.63.11
40
+ Requires-Dist: litellm>=1.74.15.post1
41
41
  Requires-Dist: markdownify>=0.13.1
42
42
  Requires-Dist: mcp-proxy>=0.5.0
43
43
  Requires-Dist: mcp>=1.6.0
44
- Requires-Dist: minify-tw-html>=0.1.3
45
44
  Requires-Dist: openai>=1.66.3
46
45
  Requires-Dist: pandas>=2.2.3
47
46
  Requires-Dist: patch-ng>=1.18.1
@@ -65,11 +64,13 @@ Requires-Dist: rich>=14.0.0
65
64
  Requires-Dist: ripgrepy>=2.1.0
66
65
  Requires-Dist: send2trash>=1.8.3
67
66
  Requires-Dist: setproctitle>=1.3.5
67
+ Requires-Dist: sidematter-format>=0.0.1
68
68
  Requires-Dist: strif>=3.0.1
69
69
  Requires-Dist: tenacity>=9.0.0
70
70
  Requires-Dist: thefuzz>=0.22.1
71
71
  Requires-Dist: tiktoken>=0.9.0
72
72
  Requires-Dist: tldr>=3.3.0
73
+ Requires-Dist: tminify>=0.1.6
73
74
  Requires-Dist: typing-extensions>=4.12.2
74
75
  Requires-Dist: uvicorn>=0.34.0
75
76
  Requires-Dist: xonsh>=0.19.3
@@ -1,13 +1,13 @@
1
1
  kash/__init__.py,sha256=hplHtnRqt1MpGIgKv3WZb9YoCoMPGtnNGtu8Eb9G6zI,110
2
2
  kash/__main__.py,sha256=83JiHvCNK7BAwEkaTD0kVekj7PEMucvCyquSl4p-1QA,78
3
- kash/actions/__init__.py,sha256=a4pQw8O-Y3q5N4Qg2jUV0xEZLX6d164FQhZ6zizY9fE,1357
3
+ kash/actions/__init__.py,sha256=t3navovxzBkHxx0tQv7-97mXKl_kZmmXAIWszEeU77U,2725
4
4
  kash/actions/core/assistant_chat.py,sha256=28G20cSr7Z94cltouTPve5TXY3km0lACrRvpLE27fK8,1837
5
5
  kash/actions/core/chat.py,sha256=yCannBFa0cSpR_in-XSSuMm1x2ZZQUCKmlqzhsUfpOo,2696
6
6
  kash/actions/core/combine_docs.py,sha256=5bTU7n_ICavvTXfC7fs5BDMeZYn7Xh5FkU7DVQqDHAQ,1536
7
7
  kash/actions/core/concat_docs.py,sha256=Umx3VzFiHJGY-76AEs4ju_1HnB9SbQsBux03Mkeig24,1345
8
8
  kash/actions/core/format_markdown_template.py,sha256=ZJbtyTSypPo2ewLiGRSyIpVf711vQMhI_-Ng-FgCs80,2991
9
9
  kash/actions/core/markdownify_html.py,sha256=luMXwwaY6E8oidgdrwV6KSgzdG0iX2JKS5aTNYDdZpA,1810
10
- kash/actions/core/minify_html.py,sha256=99r3SjpI2NQP7e5MnMixAiT5lxPx7t2nyJvJi6Yps6w,1365
10
+ kash/actions/core/minify_html.py,sha256=F8TOn9DGSa6fLy27ABzDgOMN-BMZ386N0MzvGe1sU8k,1349
11
11
  kash/actions/core/readability.py,sha256=ljdB2rOpzfKU2FpEJ2UELIzcdOAWvdUjFsxoHRTE3xo,989
12
12
  kash/actions/core/render_as_html.py,sha256=CIPGKCjUEVNsnXmpqHCUnjGwTfEfOyCXxlYFUN8mahY,1870
13
13
  kash/actions/core/show_webpage.py,sha256=Ggba9jkx9U-FZOcuL0lkS-SwtPNUyxVsGdeQrqwWs1s,887
@@ -23,7 +23,7 @@ kash/commands/base/browser_commands.py,sha256=iYvpW4D_tlhW_p0cq3A6YO9UGCdHtvzIQi
23
23
  kash/commands/base/debug_commands.py,sha256=9I5W3SMQvsnpcs-b6CJCYu1Ydl6gIoTUcDZxvn1dN3g,7643
24
24
  kash/commands/base/diff_commands.py,sha256=gOeSyCPg95LBnL6JobCR7lQHNS_c-29bDo1aIJkfyGw,4913
25
25
  kash/commands/base/files_command.py,sha256=fBuZ8sLqmfH8QekGe-P11mZ4jPxRLi3rLKhZqpdwQ5g,16759
26
- kash/commands/base/general_commands.py,sha256=KaCbzk7o-ejwXE_H3PB3MrN00uTinP3T8uHKYrGPrIw,6946
26
+ kash/commands/base/general_commands.py,sha256=Y0Vdn5jIWHFWVFGPXZA9XkoTu5uBFiH0-2LNFbslM0w,7011
27
27
  kash/commands/base/logs_commands.py,sha256=IyNgxaAoa5LlS-VxD_x8bXTVbD04pT8qEHlIJNM09UU,2963
28
28
  kash/commands/base/model_commands.py,sha256=d17a2NvfDbwV1y8gyZVsOtX-j5H5we5OEXM9TxTqvBs,1790
29
29
  kash/commands/base/reformat_command.py,sha256=fhGSfC8KyPsEcKWq6lXXlXSIPRw1CweLIFsS3AmYGYU,1869
@@ -35,16 +35,16 @@ kash/commands/help/assistant_commands.py,sha256=YYIiTxFju4ZF11HXztDe4McaAuPrIkfB
35
35
  kash/commands/help/doc_commands.py,sha256=7lKR7mzue2N7pSkNqblpFJy892fS5N6jWVOHqeXziHw,2466
36
36
  kash/commands/help/help_commands.py,sha256=eJTpIhXck123PAUq2k-D3Q6UL6IQ8atOVYurLi2GD0A,4229
37
37
  kash/commands/help/logo.py,sha256=4K3pPIiNlPIgdNeOgdIGbJQCKmqCEsDOhuWPH51msWo,3377
38
- kash/commands/help/welcome.py,sha256=uM2UMtHG4oXTxU8IFlFbTOTmR5_XTCUtT828V_tKMsk,920
38
+ kash/commands/help/welcome.py,sha256=16pAASjc4UNbm-eKC482Co6VB8i-fSwII8XYrW9JbHA,934
39
39
  kash/commands/workspace/selection_commands.py,sha256=nZzA-H7Pk8kqSJVRlX7j1m6cZX-e0X8isOryDU41vqU,8156
40
40
  kash/commands/workspace/workspace_commands.py,sha256=xJ3Agg_tzGvH55705ovoZDYiTEO4FejWclwcsMWKitY,21965
41
41
  kash/config/__init__.py,sha256=ytly9Typ1mWV4CXfV9G3CIPtPQ02u2rpZ304L3GlFro,148
42
42
  kash/config/capture_output.py,sha256=ud3uUVNuDicHj3mI_nBUBO-VmOrxtBdA3z-I3D1lSCU,2398
43
- kash/config/colors.py,sha256=AIGGqV6gORIwZjH8vsnsXBBUAEgRyYI4EH6PDUteFMo,13621
43
+ kash/config/colors.py,sha256=cV3LRBegDZxZXjV-XEjc3fystFY_defhz1LN8QPdaKc,13727
44
44
  kash/config/env_settings.py,sha256=uhCdfs9-TzJ15SzbuIQP1yIORaLUqYXCxh9qq_Z8cJc,996
45
45
  kash/config/init.py,sha256=aE4sZ6DggBmmoZEx9C5mQKrEbcDiswX--HF7pfCFKzc,526
46
46
  kash/config/lazy_imports.py,sha256=MCZXLnKvNyfHi0k7MU5rNwcdJtUF28naCixuogsAOAA,805
47
- kash/config/logger.py,sha256=M5_w7LTxHO60VqLVM0yqu8pK6FHU-Twt4wfoJwuxWbY,12102
47
+ kash/config/logger.py,sha256=5_1ePJwfwIifoYQ_OWYIxTe2AM0XdmDUe4JXkH52bpg,12190
48
48
  kash/config/logger_basic.py,sha256=Gsxitz7xeMGCUr5qjWK6y72qeMsIz4mcDZP5xyzK0WU,1598
49
49
  kash/config/logo.txt,sha256=P4RO1cJ9HRF1BavTp3Kae9iByDNhzhEC-qLAa6ww1RA,217
50
50
  kash/config/server_config.py,sha256=eQ1yxDk031QI0Efp0I1VetqQd9wG7MrLVBCHFm4gp2g,1790
@@ -52,7 +52,7 @@ kash/config/settings.py,sha256=Tja5MNZJDjo5SRaCngfQQFTTjmVGUlmkCZ7UEAhvXqw,9087
52
52
  kash/config/setup.py,sha256=zFxfTPG1cbsozuwUkIyAYebxuHhpYCiaexHnYnYJG1c,3524
53
53
  kash/config/suppress_warnings.py,sha256=yty5ZodMLIpmjphRtcVmRamXfiWbyfga9annve6qxb0,1475
54
54
  kash/config/text_styles.py,sha256=1qIrMgDYYuBoVj9kFCaEEOca_Ibz5VnPVNI-xTSQnlk,13840
55
- kash/config/unified_live.py,sha256=EV_Y0_WqeVFoJ_s4ZEHhGBNeaMyzEcO6hNAVp6rHNug,8456
55
+ kash/config/unified_live.py,sha256=tUEnTWMSYKYSJkEoAPbaJET-bJ1HnfU2Ar-XeyBOtlo,8420
56
56
  kash/docs/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
57
57
  kash/docs/all_docs.py,sha256=NutfgU8VOA7_K2HX18FoOHVvvLL14dALoCxK9qDbQ04,3157
58
58
  kash/docs/load_actions_info.py,sha256=D9uv8gdBtkBmdbFZeyIigsupPF9_WfidHVwWQrlggI0,937
@@ -148,7 +148,7 @@ kash/mcp/mcp_cli.py,sha256=UC0Jwd7DLxx2zEFj0hK1UWPkXXXGntV1te33CensyHM,3849
148
148
  kash/mcp/mcp_main.py,sha256=6PhjKwp631mezDTUAd-pL8lUZx9Gl7yCrCQFW61pqJU,3167
149
149
  kash/mcp/mcp_server_commands.py,sha256=C-gKLbUVEpF76SmW3NgjlEWoM3YaA3ARrCos5UH1Zh8,4345
150
150
  kash/mcp/mcp_server_routes.py,sha256=radxy5cc0yBmcbqAbB1LpZ0qcNtfDbtS5RTGwvgliDM,10617
151
- kash/mcp/mcp_server_sse.py,sha256=_D61cRWMuxgMrk-KxhkRLaaXXpgzJJa0sOB3uRxR0XM,5886
151
+ kash/mcp/mcp_server_sse.py,sha256=7zAOJodrCVfLtChUTRxzgxWGymQnmj1e9fRG7H_yqXg,5678
152
152
  kash/mcp/mcp_server_stdio.py,sha256=u-oeIZKwzIAGlKmBpipC-hfNQKx36Md9hST11y3AZUY,1174
153
153
  kash/media_base/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
154
154
  kash/media_base/audio_processing.py,sha256=k8V3SpQrSzdxHiInei4z6LycoAnfpQ2dttOfWhWLTX8,2874
@@ -167,7 +167,7 @@ kash/model/compound_actions_model.py,sha256=HiDK5wwCu3WwZYHATZoLEguiqwR9V6V296wi
167
167
  kash/model/concept_model.py,sha256=we2qOcy9Mv1q7XPfkDLp_CyO_-8DwAUfUYlpgy_jrFs,1011
168
168
  kash/model/exec_model.py,sha256=IlfvtQyoFRRWhWju7vdXp9J-w_NGcGtL5DhDLy9gRd8,2250
169
169
  kash/model/graph_model.py,sha256=T034y0E9OJtITd1g9zp9vll5pLscdatq6JoT08KvPZE,2724
170
- kash/model/items_model.py,sha256=wqJpHyxZFgWW7GQNiBuxfpP1df6ieZrghhu5qcDA5V4,35834
170
+ kash/model/items_model.py,sha256=UMPA4-rmkX6XXuB1bFWP7KwUE4thOEp-tnfvwJCBols,35844
171
171
  kash/model/language_list.py,sha256=I3RIbxTseVmPdhExQimimEv18Gmy2ImMbpXe0-_t1Qw,450
172
172
  kash/model/llm_actions_model.py,sha256=a29uXVNfS2CiqvM7HPdC6H9A23rSQQihAideuBLMH8g,2110
173
173
  kash/model/media_model.py,sha256=ZnlZ-FkswbAIGpUAuNqLce1WDZK-WbnwHn2ipg8x7-0,3511
@@ -176,8 +176,8 @@ kash/model/params_model.py,sha256=vSFMjWfksysEhAOQ2Ge2ZEvRqgUmIL7febxcI3-7Smg,15
176
176
  kash/model/paths_model.py,sha256=KDFm7wan7hjObHbnV2rR8-jsyLTVqbKcwFdKeLFRtdM,15889
177
177
  kash/model/preconditions_model.py,sha256=-IfsVR0NkQhq_3hUTXzK2bFYAd--3YjSwUiDKHVQQqk,2887
178
178
  kash/shell/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
179
- kash/shell/shell_main.py,sha256=nqbP8NyxtxAwh787YWhpbWelt_ObfIRZzCMK1aaQcmg,2094
180
- kash/shell/version.py,sha256=FRGs_jmzk6QiRPZfZv36SPzeyJCsVWZ_E2CKRkExazw,835
179
+ kash/shell/shell_main.py,sha256=thpGEN2kiruTiMaocdwnzfIAs-WCX-Pvi8jiea3V2q0,3896
180
+ kash/shell/version.py,sha256=Si8MgIwAwTOSdXY7znWHTsvzdR2vlZdkmcF5n_oUigE,1400
181
181
  kash/shell/completions/completion_scoring.py,sha256=-svesm2cR1AA86jYcxlynXCBZON26eUJce93FlL2nQo,10209
182
182
  kash/shell/completions/completion_types.py,sha256=FocRXd6Df3Df0nL2Y1GevMx3FsljJwbQdVgWsIngpaQ,4793
183
183
  kash/shell/completions/shell_completions.py,sha256=A0WWrm2lEwguasDMnDuaI8xGny9MhwGfNvCY3rHNUnw,8844
@@ -264,17 +264,17 @@ kash/web_gen/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
264
264
  kash/web_gen/simple_webpage.py,sha256=ks_0ljxCeS2-gAAEaUc1JEnzY3JY0nzqGFiyyqyRuZs,1537
265
265
  kash/web_gen/tabbed_webpage.py,sha256=e0GGG1bQ4CQegpJgOIT2KpyM6cmwN_BQ9eJSsi4BjgY,4945
266
266
  kash/web_gen/template_render.py,sha256=aypo6UanouftV4RpxgNm6JdquelI52fV0IlihdA3yjE,1908
267
- kash/web_gen/templates/base_styles.css.jinja,sha256=hZIr40en-eZCB9xNTChO7WDJGXdfXQyTeZXh5xvcbfY,24204
268
- kash/web_gen/templates/base_webpage.html.jinja,sha256=Iz3PkNwLHW3DRuaIrXxCovFfCcoCHR7FAStuBCnWgag,13459
267
+ kash/web_gen/templates/base_styles.css.jinja,sha256=9ftNuhUrTpS8TcxP239AqWsIhPl_i0wS0J4rhsvQkrM,24962
268
+ kash/web_gen/templates/base_webpage.html.jinja,sha256=ZP9p1S29yXNZ6CU0DYYAXUA-v6YhnUv9NLX4aYupvBE,14723
269
269
  kash/web_gen/templates/content_styles.css.jinja,sha256=1gHukwjv6PR5APX9KwNqMOBIKUjFenuudVZ8fjtavYY,4672
270
270
  kash/web_gen/templates/explain_view.html.jinja,sha256=DNw5Iw5SrhIUFRGB4qNvfcKXsBHVbEJVURGdhvyC75Q,949
271
271
  kash/web_gen/templates/item_view.html.jinja,sha256=_b51RuoBmYu7nxVq-S_zw_tv8mfQXHICGqfDWNIB9Xg,7304
272
272
  kash/web_gen/templates/simple_webpage.html.jinja,sha256=_RVu0AvrN5fK_Kz-tEi4AlPQ_wuu8-S9oFIYg_sdcec,2556
273
273
  kash/web_gen/templates/tabbed_webpage.html.jinja,sha256=umkipUXW-lDGnbV-tlDroCfCx_385PFnpbzsvwmityo,1843
274
274
  kash/web_gen/templates/components/toc_scripts.js.jinja,sha256=9AanLJaVormGi52h-k2tKJTRT4BiBGGNnw3Kmrnr40Q,10481
275
- kash/web_gen/templates/components/toc_styles.css.jinja,sha256=p53I7fIVPLlS-GO2i6O2G4ueOKDyfqqMPthH37OAVCA,7336
275
+ kash/web_gen/templates/components/toc_styles.css.jinja,sha256=SM99C9bOu11qdZ1U6hN7lLe2w_Hk6u9qNZcx2knSkgg,7553
276
276
  kash/web_gen/templates/components/tooltip_scripts.js.jinja,sha256=iz_5L5X4D4D1guotJjGVxMh5LcyOpjepw1R3nQd1NLE,32084
277
- kash/web_gen/templates/components/tooltip_styles.css.jinja,sha256=LCpJ8k1dXuDPKJF-pugNVPOtHvVOzU8DaIixOAPkHtU,14196
277
+ kash/web_gen/templates/components/tooltip_styles.css.jinja,sha256=tD-GBEFNIeVPAbbeB88bsOWzEFoThcSP5FfH9LmSAeM,14216
278
278
  kash/workspaces/__init__.py,sha256=q1gFERRZLJMA9-XSUKvB1ulauHDKqyzzc86GFLbxAuk,700
279
279
  kash/workspaces/param_state.py,sha256=vT_eGWqg2SRviIM5jqEAauznX2B5Xt2nHHu2oRxTcIU,746
280
280
  kash/workspaces/selections.py,sha256=rEUuQlrQ3C_54bzBSKDTTptgX8oZPqN0Ao4uaXSWA-Q,12003
@@ -284,10 +284,10 @@ kash/workspaces/workspace_output.py,sha256=MMg_KumkHKFGc0DOUFaW5ImpgqIfdlsLtvXbL
284
284
  kash/workspaces/workspace_registry.py,sha256=SQt2DZgBEu95Zj9fpy67XdJPgJyKFDCU2laSuiZswNo,2200
285
285
  kash/workspaces/workspaces.py,sha256=ypxlX2K64QOhNsta69arlvKbiVpUW_4CDeX_sEcIQbg,6907
286
286
  kash/xonsh_custom/command_nl_utils.py,sha256=6Xcx98HXL5HywziHi0XskwFx6kfvz7oCmMX-siJib1A,3392
287
- kash/xonsh_custom/custom_shell.py,sha256=-YGZz61HJQuYllYB7CKc9EyYBywei5lOkoWz8akMxv8,19100
287
+ kash/xonsh_custom/custom_shell.py,sha256=xthM_CAHw6FNlXx-vicLXfRgMHK2f7MpLprhc8PCD84,19005
288
288
  kash/xonsh_custom/customize_prompt.py,sha256=u-jRY-ftXYflBkbJVetEg6GYelPUvqZEpjrPRUTfy8w,6896
289
289
  kash/xonsh_custom/load_into_xonsh.py,sha256=Z_PAaW_Uv-PDRKdw9E_7dC1eMe6FbwwIUioxyS1Sp_g,3596
290
- kash/xonsh_custom/shell_load_commands.py,sha256=bndmVEecIhuzQBI3OUDpH4ac7DXGkAMUVqXXcbrmEqI,4719
290
+ kash/xonsh_custom/shell_load_commands.py,sha256=2SzigO-IDK5QTBhAkv7bL4hPuRLWIT0r5D9t4mrXANY,4673
291
291
  kash/xonsh_custom/shell_which.py,sha256=zRaLhFVg9HEDFXo4dqWKwX07YpfPh25kopeG_fgctOE,1926
292
292
  kash/xonsh_custom/xonsh_completers.py,sha256=jxsc279DwZUHm0-iCnCtvbzqJBtq8zu0FUls5J1BA8o,17959
293
293
  kash/xonsh_custom/xonsh_env.py,sha256=KEob1vxlT4gBndYrLPP3deQtANA5Sx6PPE9Q08r4ua8,871
@@ -296,8 +296,8 @@ kash/xonsh_custom/xonsh_modern_tools.py,sha256=mj_b34LZXfE8MJe9EpDmp5JZ0tDM1biYN
296
296
  kash/xonsh_custom/xonsh_ranking_completer.py,sha256=ZRGiAfoEgqgnlq2-ReUVEaX5oOgW1DQ9WxIv2OJLuTo,5620
297
297
  kash/xontrib/fnm.py,sha256=V2tsOdmIDgbFbZSfMLpsvDIwwJJqiYnOkOySD1cXNXw,3700
298
298
  kash/xontrib/kash_extension.py,sha256=FLIMlgR3C_6A1fwKE-Ul0nmmpJSszVPbAriinUyQ8Zg,1896
299
- kash_shell-0.3.26.dist-info/METADATA,sha256=Y5rithuIF2tpjy9RwzJDF1VS7ua1IOotVBFp62YDo9I,33041
300
- kash_shell-0.3.26.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
301
- kash_shell-0.3.26.dist-info/entry_points.txt,sha256=SQraWDAo8SqYpthLXThei0mf_hGGyhYBUO-Er_0HcwI,85
302
- kash_shell-0.3.26.dist-info/licenses/LICENSE,sha256=rCh2PsfYeiU6FK_0wb58kHGm_Fj5c43fdcHEexiVzIo,34562
303
- kash_shell-0.3.26.dist-info/RECORD,,
299
+ kash_shell-0.3.28.dist-info/METADATA,sha256=IM3U_GjrsZruEj5jtyFT3grUb6TGe-kRzzwO2MdLIxY,33080
300
+ kash_shell-0.3.28.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
301
+ kash_shell-0.3.28.dist-info/entry_points.txt,sha256=SQraWDAo8SqYpthLXThei0mf_hGGyhYBUO-Er_0HcwI,85
302
+ kash_shell-0.3.28.dist-info/licenses/LICENSE,sha256=rCh2PsfYeiU6FK_0wb58kHGm_Fj5c43fdcHEexiVzIo,34562
303
+ kash_shell-0.3.28.dist-info/RECORD,,