codebind 0.4.2__py3-none-any.whl → 0.4.3__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.
codebind/extension.py CHANGED
@@ -2,6 +2,9 @@
2
2
 
3
3
  from __future__ import annotations
4
4
 
5
+ import json
6
+ import os
7
+ from pathlib import Path
5
8
  from typing import Any
6
9
 
7
10
  from IPython.core.interactiveshell import InteractiveShell
@@ -14,8 +17,28 @@ from .session import Session
14
17
  _NAMESPACE_ATTRIBUTE = "_codebind_extension_namespace"
15
18
 
16
19
 
20
+ def _models_path() -> Path:
21
+ configured = os.environ.get("XDG_CONFIG_HOME")
22
+ if configured:
23
+ config_home = Path(configured).expanduser()
24
+ if config_home.is_absolute():
25
+ return config_home / "codebind" / "models.json"
26
+ return Path.home() / ".config" / "codebind" / "models.json"
27
+
28
+
29
+ def _load_models() -> Models:
30
+ path = _models_path()
31
+ if not path.exists():
32
+ return Models()
33
+ values = json.loads(path.read_text())
34
+ if not isinstance(values, dict):
35
+ raise ValueError(f"Codebind model configuration must be a JSON object: {path}")
36
+ return Models(values)
37
+
38
+
17
39
  def load_ipython_extension(ipython: InteractiveShell) -> None:
18
40
  """Load Codebind into the active IPython user namespace."""
41
+ models = _load_models()
19
42
  previous = getattr(ipython, _NAMESPACE_ATTRIBUTE, None)
20
43
  if isinstance(previous, dict):
21
44
  previous_chat = previous.get("chat")
@@ -26,6 +49,7 @@ def load_ipython_extension(ipython: InteractiveShell) -> None:
26
49
  namespace: dict[str, Any] = {
27
50
  "chat": Session(shell=ipython, bridge=bridge),
28
51
  "Models": Models,
52
+ "models": models,
29
53
  }
30
54
  ipython.push(namespace)
31
55
  setattr(ipython, _NAMESPACE_ATTRIBUTE, namespace)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: codebind
3
- Version: 0.4.2
3
+ Version: 0.4.3
4
4
  Summary: A frontend-neutral model loop for persistent IPython sessions.
5
5
  Keywords: ai,ipython,llm,repl,agents
6
6
  Author: Giovanni Gravili
@@ -47,11 +47,9 @@ After installation, start ordinary IPython with the Codebind extension from any
47
47
  codebind
48
48
  ```
49
49
 
50
- It opens standard IPython with `chat` and `Models` in the user namespace. All normal IPython command-line options remain available.
50
+ It opens standard IPython with `chat`, `models`, and `Models` in the user namespace. `models` loads provider values from `$XDG_CONFIG_HOME/codebind/models.json`, or `~/.config/codebind/models.json` when `XDG_CONFIG_HOME` is unset. Keep that credential file readable only by its owner. All normal IPython command-line options remain available.
51
51
 
52
52
  ```python
53
- models = Models({"openai": "OPENAI_API_KEY"})
54
-
55
53
  chat.send(
56
54
  "Inspect this project and tell me what to implement first.",
57
55
  models.chat("openai/gpt-5", reasoning_effort="medium"),
@@ -65,7 +63,7 @@ Codebind does not load files or construct a project prompt automatically. The us
65
63
  Start JupyterLab with Codebind from any directory without a permanent installation:
66
64
 
67
65
  ```console
68
- uvx --from jupyterlab --with codebind jupyter lab
66
+ uvx --from jupyterlab --with codebind --with 'nbconvert[webpdf]' jupyter lab
69
67
  ```
70
68
 
71
69
  Or install both packages into the same environment, then start JupyterLab normally:
@@ -84,7 +82,6 @@ Load Codebind in a notebook:
84
82
  Run that cell once so JupyterLab can connect to the extension, then use Codebind in later cells:
85
83
 
86
84
  ```python
87
- models = Models({"openai": "OPENAI_API_KEY"})
88
85
  model = models.chat("openai/gpt-5")
89
86
  await chat.asend("Inspect the current notebook state.", model)
90
87
  ```
@@ -111,6 +108,6 @@ chat.send(
111
108
  )
112
109
  ```
113
110
 
114
- The authorization remains in memory for this session. Persistent credential storage belongs to the host application.
111
+ The authorization remains in memory for this session. Save provider values as a JSON object in Codebind's XDG configuration file and reload the extension to expose them through `models`.
115
112
 
116
113
  OpenAI officially supports ChatGPT subscription sign-in for Codex clients. Models Provider reproduces that account-access boundary for this library; it is separate from the public, pay-as-you-go OpenAI API and may require compatibility updates when the Codex account protocol changes.
@@ -2,18 +2,18 @@ codebind/__init__.py,sha256=GNO_K5EPAdgiK2CWsPVVY-3bAmH2TnFJ9ReAWgSbnqM,514
2
2
  codebind/cli.py,sha256=9LOR1L3P8sPsOOgsnpbOsA1PNUZdAj1Z9ROFKeo3EV8,423
3
3
  codebind/display.py,sha256=IpxcElyNcr5olRIatEduN_d-sRwpsMlaq1UtrOXocQA,494
4
4
  codebind/execution.py,sha256=b1U0iT0e9fDpvGZclGGihod_iLFjJ7wLUkXhmawgeRs,11968
5
- codebind/extension.py,sha256=elIDW_zl5o3uyil1tEnJ0A5jVkADalqPWI_qcDw4xhY,1460
5
+ codebind/extension.py,sha256=xzdBpUtQnjJVqCivuW3uruTURrkKhMnY_YsHFHl53IQ,2176
6
6
  codebind/jupyter.py,sha256=xuoiV2-pqtcb_dWXvaaVrlSvqcYfqRYtbX4B-Zh_pBA,3272
7
7
  codebind/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
8
8
  codebind/session.py,sha256=6KK2d55XsKaq5IVRQmUp5Pzdg-O76bAZvCYgxBU2BN0,7455
9
- codebind-0.4.2.dist-info/licenses/LICENSE,sha256=ujX46e0LFBIBTnCDY0u3Q7LV363B7CiI7QJZxIkEXlk,1073
10
- codebind-0.4.2.data/data/share/jupyter/labextensions/codebind-jupyterlab/install.json,sha256=78rEThkfrk1pXtekX5WrG9_Y0lJYi5XBEm8n9athpFE,164
11
- codebind-0.4.2.data/data/share/jupyter/labextensions/codebind-jupyterlab/package.json,sha256=HYr80rRV4byoPUvhf5r9swwnssr7eGxIay227Cusyqo,1152
12
- codebind-0.4.2.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/590.6544266cd73a003b.js,sha256=zrQdGY0320_MGN8KRf8dzMXCjXI_6jtZoAnW4UhDquo,2771
13
- codebind-0.4.2.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/remoteEntry.6f017385dfc989f1.js,sha256=Cwm6yVfy68shv0OTb6yIbHwV5FxozSz-jO9gf9WE0vc,11087
14
- codebind-0.4.2.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/style.js,sha256=Opy15wyuR_ABqsrk-cOcOj2yZtvtq0r36aDkErnloD0,113
15
- codebind-0.4.2.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/third-party-licenses.json,sha256=MNToQfru1YnHAie-2Virp23yWsc5co3qG0IzrO6SEfw,20
16
- codebind-0.4.2.dist-info/WHEEL,sha256=R1d3uUTbmXM1FHXH_itQashbrqrOSVj-hvBCpmkIIGE,81
17
- codebind-0.4.2.dist-info/entry_points.txt,sha256=GiPcU63sULDlywJSKigAS4M3vaziYIrubXOb3fAg2_c,48
18
- codebind-0.4.2.dist-info/METADATA,sha256=oWEAHVAAIlHYBAE_kcRViMyLALj56VMMxIWdD5PF_Ys,4062
19
- codebind-0.4.2.dist-info/RECORD,,
9
+ codebind-0.4.3.dist-info/licenses/LICENSE,sha256=ujX46e0LFBIBTnCDY0u3Q7LV363B7CiI7QJZxIkEXlk,1073
10
+ codebind-0.4.3.data/data/share/jupyter/labextensions/codebind-jupyterlab/install.json,sha256=78rEThkfrk1pXtekX5WrG9_Y0lJYi5XBEm8n9athpFE,164
11
+ codebind-0.4.3.data/data/share/jupyter/labextensions/codebind-jupyterlab/package.json,sha256=HYr80rRV4byoPUvhf5r9swwnssr7eGxIay227Cusyqo,1152
12
+ codebind-0.4.3.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/590.6544266cd73a003b.js,sha256=zrQdGY0320_MGN8KRf8dzMXCjXI_6jtZoAnW4UhDquo,2771
13
+ codebind-0.4.3.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/remoteEntry.6f017385dfc989f1.js,sha256=Cwm6yVfy68shv0OTb6yIbHwV5FxozSz-jO9gf9WE0vc,11087
14
+ codebind-0.4.3.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/style.js,sha256=Opy15wyuR_ABqsrk-cOcOj2yZtvtq0r36aDkErnloD0,113
15
+ codebind-0.4.3.data/data/share/jupyter/labextensions/codebind-jupyterlab/static/third-party-licenses.json,sha256=MNToQfru1YnHAie-2Virp23yWsc5co3qG0IzrO6SEfw,20
16
+ codebind-0.4.3.dist-info/WHEEL,sha256=R1d3uUTbmXM1FHXH_itQashbrqrOSVj-hvBCpmkIIGE,81
17
+ codebind-0.4.3.dist-info/entry_points.txt,sha256=GiPcU63sULDlywJSKigAS4M3vaziYIrubXOb3fAg2_c,48
18
+ codebind-0.4.3.dist-info/METADATA,sha256=fc0mvklMLUXzsIUZLuAaLJP10eI4HnWu-pCa94enbEE,4277
19
+ codebind-0.4.3.dist-info/RECORD,,