openai-sdk-helpers 0.0.8__py3-none-any.whl → 0.1.0__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.
- openai_sdk_helpers/__init__.py +90 -2
- openai_sdk_helpers/agent/__init__.py +8 -4
- openai_sdk_helpers/agent/base.py +80 -45
- openai_sdk_helpers/agent/config.py +6 -4
- openai_sdk_helpers/agent/{project_manager.py → coordination.py} +29 -45
- openai_sdk_helpers/agent/prompt_utils.py +7 -1
- openai_sdk_helpers/agent/runner.py +67 -141
- openai_sdk_helpers/agent/search/__init__.py +33 -0
- openai_sdk_helpers/agent/search/base.py +297 -0
- openai_sdk_helpers/agent/{vector_search.py → search/vector.py} +89 -157
- openai_sdk_helpers/agent/{web_search.py → search/web.py} +77 -156
- openai_sdk_helpers/agent/summarizer.py +29 -8
- openai_sdk_helpers/agent/translator.py +40 -13
- openai_sdk_helpers/agent/validation.py +32 -8
- openai_sdk_helpers/async_utils.py +132 -0
- openai_sdk_helpers/config.py +101 -65
- openai_sdk_helpers/context_manager.py +241 -0
- openai_sdk_helpers/enums/__init__.py +9 -1
- openai_sdk_helpers/enums/base.py +67 -8
- openai_sdk_helpers/environment.py +33 -6
- openai_sdk_helpers/errors.py +133 -0
- openai_sdk_helpers/logging_config.py +105 -0
- openai_sdk_helpers/prompt/__init__.py +10 -71
- openai_sdk_helpers/prompt/base.py +222 -0
- openai_sdk_helpers/response/__init__.py +38 -3
- openai_sdk_helpers/response/base.py +363 -210
- openai_sdk_helpers/response/config.py +318 -0
- openai_sdk_helpers/response/messages.py +56 -40
- openai_sdk_helpers/response/runner.py +77 -33
- openai_sdk_helpers/response/tool_call.py +62 -27
- openai_sdk_helpers/response/vector_store.py +27 -14
- openai_sdk_helpers/retry.py +175 -0
- openai_sdk_helpers/streamlit_app/__init__.py +19 -2
- openai_sdk_helpers/streamlit_app/app.py +114 -39
- openai_sdk_helpers/streamlit_app/config.py +502 -0
- openai_sdk_helpers/streamlit_app/streamlit_web_search.py +5 -6
- openai_sdk_helpers/structure/__init__.py +72 -3
- openai_sdk_helpers/structure/agent_blueprint.py +82 -19
- openai_sdk_helpers/structure/base.py +208 -93
- openai_sdk_helpers/structure/plan/__init__.py +29 -1
- openai_sdk_helpers/structure/plan/enum.py +41 -5
- openai_sdk_helpers/structure/plan/helpers.py +172 -0
- openai_sdk_helpers/structure/plan/plan.py +109 -49
- openai_sdk_helpers/structure/plan/task.py +38 -6
- openai_sdk_helpers/structure/plan/types.py +15 -0
- openai_sdk_helpers/structure/prompt.py +21 -2
- openai_sdk_helpers/structure/responses.py +52 -11
- openai_sdk_helpers/structure/summary.py +55 -7
- openai_sdk_helpers/structure/validation.py +34 -6
- openai_sdk_helpers/structure/vector_search.py +132 -18
- openai_sdk_helpers/structure/web_search.py +125 -13
- openai_sdk_helpers/tools.py +193 -0
- openai_sdk_helpers/types.py +57 -0
- openai_sdk_helpers/utils/__init__.py +34 -1
- openai_sdk_helpers/utils/core.py +296 -34
- openai_sdk_helpers/validation.py +302 -0
- openai_sdk_helpers/vector_storage/__init__.py +21 -1
- openai_sdk_helpers/vector_storage/cleanup.py +25 -13
- openai_sdk_helpers/vector_storage/storage.py +123 -64
- openai_sdk_helpers/vector_storage/types.py +20 -19
- openai_sdk_helpers-0.1.0.dist-info/METADATA +550 -0
- openai_sdk_helpers-0.1.0.dist-info/RECORD +69 -0
- openai_sdk_helpers/streamlit_app/configuration.py +0 -324
- openai_sdk_helpers-0.0.8.dist-info/METADATA +0 -194
- openai_sdk_helpers-0.0.8.dist-info/RECORD +0 -55
- {openai_sdk_helpers-0.0.8.dist-info → openai_sdk_helpers-0.1.0.dist-info}/WHEEL +0 -0
- {openai_sdk_helpers-0.0.8.dist-info → openai_sdk_helpers-0.1.0.dist-info}/licenses/LICENSE +0 -0
|
@@ -1,324 +0,0 @@
|
|
|
1
|
-
"""Configuration loading for the example Streamlit chat app."""
|
|
2
|
-
|
|
3
|
-
from __future__ import annotations
|
|
4
|
-
|
|
5
|
-
import importlib.util
|
|
6
|
-
from pathlib import Path
|
|
7
|
-
from types import ModuleType
|
|
8
|
-
from typing import Callable, Sequence, cast
|
|
9
|
-
from pydantic import BaseModel, ConfigDict, Field, field_validator, model_validator
|
|
10
|
-
|
|
11
|
-
from openai_sdk_helpers.response.base import BaseResponse
|
|
12
|
-
from openai_sdk_helpers.structure.base import BaseStructure
|
|
13
|
-
from openai_sdk_helpers.utils import ensure_list
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
class StreamlitAppConfig(BaseModel):
|
|
17
|
-
"""Validated configuration for the config-driven Streamlit application.
|
|
18
|
-
|
|
19
|
-
Methods
|
|
20
|
-
-------
|
|
21
|
-
normalized_vector_stores()
|
|
22
|
-
Return configured system vector stores as a list of names.
|
|
23
|
-
create_response()
|
|
24
|
-
Instantiate the configured ``BaseResponse``.
|
|
25
|
-
load_app_config(config_path)
|
|
26
|
-
Load, validate, and return the Streamlit application configuration.
|
|
27
|
-
"""
|
|
28
|
-
|
|
29
|
-
model_config = ConfigDict(extra="forbid", arbitrary_types_allowed=True)
|
|
30
|
-
|
|
31
|
-
response: BaseResponse[BaseStructure] | type[BaseResponse] | Callable | None = (
|
|
32
|
-
Field(
|
|
33
|
-
default=None,
|
|
34
|
-
description=(
|
|
35
|
-
"Configured ``BaseResponse`` subclass, instance, or callable that returns"
|
|
36
|
-
" a response instance."
|
|
37
|
-
),
|
|
38
|
-
)
|
|
39
|
-
)
|
|
40
|
-
display_title: str = Field(
|
|
41
|
-
default="Example copilot",
|
|
42
|
-
description="Title displayed at the top of the Streamlit page.",
|
|
43
|
-
)
|
|
44
|
-
description: str | None = Field(
|
|
45
|
-
default=None,
|
|
46
|
-
description="Optional short description shown beneath the title.",
|
|
47
|
-
)
|
|
48
|
-
system_vector_store: list[str] | None = Field(
|
|
49
|
-
default=None,
|
|
50
|
-
description=(
|
|
51
|
-
"Optional vector store names to attach as system context for "
|
|
52
|
-
"file search tools."
|
|
53
|
-
),
|
|
54
|
-
)
|
|
55
|
-
preserve_vector_stores: bool = Field(
|
|
56
|
-
default=False,
|
|
57
|
-
description="When ``True``, skip automatic vector store cleanup on close.",
|
|
58
|
-
)
|
|
59
|
-
model: str | None = Field(
|
|
60
|
-
default=None,
|
|
61
|
-
description="Optional model hint for display alongside the chat interface.",
|
|
62
|
-
)
|
|
63
|
-
|
|
64
|
-
@field_validator("system_vector_store", mode="before")
|
|
65
|
-
@classmethod
|
|
66
|
-
def validate_vector_store(
|
|
67
|
-
cls, value: Sequence[str] | str | None
|
|
68
|
-
) -> list[str] | None:
|
|
69
|
-
"""Normalize configured vector stores to a list of names.
|
|
70
|
-
|
|
71
|
-
Parameters
|
|
72
|
-
----------
|
|
73
|
-
value : Sequence[str] | str | None
|
|
74
|
-
Raw value provided by the configuration module.
|
|
75
|
-
|
|
76
|
-
Returns
|
|
77
|
-
-------
|
|
78
|
-
list[str] | None
|
|
79
|
-
Normalized list of vector store names.
|
|
80
|
-
|
|
81
|
-
Raises
|
|
82
|
-
------
|
|
83
|
-
TypeError
|
|
84
|
-
If any entry cannot be coerced to ``str``.
|
|
85
|
-
"""
|
|
86
|
-
if value is None:
|
|
87
|
-
return None
|
|
88
|
-
stores = ensure_list(value)
|
|
89
|
-
if not all(isinstance(store, str) for store in stores):
|
|
90
|
-
raise ValueError("system_vector_store values must be strings.")
|
|
91
|
-
return list(stores)
|
|
92
|
-
|
|
93
|
-
@field_validator("response")
|
|
94
|
-
@classmethod
|
|
95
|
-
def validate_response(
|
|
96
|
-
cls, value: BaseResponse[BaseStructure] | type[BaseResponse] | Callable | None
|
|
97
|
-
) -> BaseResponse[BaseStructure] | type[BaseResponse] | Callable | None:
|
|
98
|
-
"""Ensure the configuration provides a valid response source."""
|
|
99
|
-
if value is None:
|
|
100
|
-
return None
|
|
101
|
-
if isinstance(value, BaseResponse):
|
|
102
|
-
return value
|
|
103
|
-
if isinstance(value, type) and issubclass(value, BaseResponse):
|
|
104
|
-
return value
|
|
105
|
-
if callable(value):
|
|
106
|
-
return value
|
|
107
|
-
raise TypeError("response must be a BaseResponse, subclass, or callable")
|
|
108
|
-
|
|
109
|
-
def normalized_vector_stores(self) -> list[str]:
|
|
110
|
-
"""Return configured system vector stores as a list.
|
|
111
|
-
|
|
112
|
-
Returns
|
|
113
|
-
-------
|
|
114
|
-
list[str]
|
|
115
|
-
Vector store names or an empty list when none are configured.
|
|
116
|
-
"""
|
|
117
|
-
return list(self.system_vector_store or [])
|
|
118
|
-
|
|
119
|
-
@model_validator(mode="after")
|
|
120
|
-
def ensure_response(self) -> "StreamlitAppConfig":
|
|
121
|
-
"""Validate that a response source is provided."""
|
|
122
|
-
if self.response is None:
|
|
123
|
-
raise ValueError("response must be provided.")
|
|
124
|
-
return self
|
|
125
|
-
|
|
126
|
-
def create_response(self) -> BaseResponse[BaseStructure]:
|
|
127
|
-
"""Instantiate and return the configured response instance.
|
|
128
|
-
|
|
129
|
-
Returns
|
|
130
|
-
-------
|
|
131
|
-
BaseResponse[BaseStructure]
|
|
132
|
-
Active response instance.
|
|
133
|
-
|
|
134
|
-
Raises
|
|
135
|
-
------
|
|
136
|
-
TypeError
|
|
137
|
-
If the configured ``response`` cannot produce a ``BaseResponse``.
|
|
138
|
-
"""
|
|
139
|
-
return _instantiate_response(self.response)
|
|
140
|
-
|
|
141
|
-
@staticmethod
|
|
142
|
-
def load_app_config(
|
|
143
|
-
config_path: Path,
|
|
144
|
-
) -> "StreamlitAppConfig":
|
|
145
|
-
"""Load, validate, and return the Streamlit application configuration.
|
|
146
|
-
|
|
147
|
-
Parameters
|
|
148
|
-
----------
|
|
149
|
-
config_path : Path
|
|
150
|
-
Filesystem path to the configuration module.
|
|
151
|
-
|
|
152
|
-
Returns
|
|
153
|
-
-------
|
|
154
|
-
StreamlitAppConfig
|
|
155
|
-
Validated configuration derived from ``config_path``.
|
|
156
|
-
"""
|
|
157
|
-
module = _import_config_module(config_path)
|
|
158
|
-
return _extract_config(module)
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
def _import_config_module(config_path: Path) -> ModuleType:
|
|
162
|
-
"""Import the configuration module from ``config_path``.
|
|
163
|
-
|
|
164
|
-
Parameters
|
|
165
|
-
----------
|
|
166
|
-
config_path : Path
|
|
167
|
-
Filesystem path pointing to the configuration module.
|
|
168
|
-
|
|
169
|
-
Returns
|
|
170
|
-
-------
|
|
171
|
-
ModuleType
|
|
172
|
-
Loaded Python module containing application configuration.
|
|
173
|
-
|
|
174
|
-
Raises
|
|
175
|
-
------
|
|
176
|
-
FileNotFoundError
|
|
177
|
-
If ``config_path`` does not exist.
|
|
178
|
-
ImportError
|
|
179
|
-
If the module cannot be imported.
|
|
180
|
-
"""
|
|
181
|
-
if not config_path.exists():
|
|
182
|
-
raise FileNotFoundError(f"Configuration file not found at '{config_path}'.")
|
|
183
|
-
|
|
184
|
-
spec = importlib.util.spec_from_file_location(config_path.stem, config_path)
|
|
185
|
-
if spec is None or spec.loader is None:
|
|
186
|
-
raise ImportError(f"Unable to load configuration module at '{config_path}'.")
|
|
187
|
-
|
|
188
|
-
module = importlib.util.module_from_spec(spec)
|
|
189
|
-
spec.loader.exec_module(module)
|
|
190
|
-
return module
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
def _extract_config(module: ModuleType) -> StreamlitAppConfig:
|
|
194
|
-
"""Extract a validated :class:`StreamlitAppConfig` from ``module``.
|
|
195
|
-
|
|
196
|
-
Parameters
|
|
197
|
-
----------
|
|
198
|
-
module : ModuleType
|
|
199
|
-
Module loaded from the configuration path.
|
|
200
|
-
|
|
201
|
-
Returns
|
|
202
|
-
-------
|
|
203
|
-
StreamlitAppConfig
|
|
204
|
-
Parsed and validated configuration instance.
|
|
205
|
-
|
|
206
|
-
Raises
|
|
207
|
-
------
|
|
208
|
-
ValueError
|
|
209
|
-
If ``APP_CONFIG`` is missing from the module.
|
|
210
|
-
TypeError
|
|
211
|
-
If ``APP_CONFIG`` is neither a mapping nor ``StreamlitAppConfig`` instance.
|
|
212
|
-
"""
|
|
213
|
-
if not hasattr(module, "APP_CONFIG"):
|
|
214
|
-
raise ValueError("APP_CONFIG must be defined in the configuration module.")
|
|
215
|
-
|
|
216
|
-
raw_config = getattr(module, "APP_CONFIG")
|
|
217
|
-
if isinstance(raw_config, StreamlitAppConfig):
|
|
218
|
-
return raw_config
|
|
219
|
-
if isinstance(raw_config, dict):
|
|
220
|
-
return _config_from_mapping(raw_config)
|
|
221
|
-
if isinstance(raw_config, BaseResponse):
|
|
222
|
-
return StreamlitAppConfig(response=raw_config)
|
|
223
|
-
if isinstance(raw_config, type) and issubclass(raw_config, BaseResponse):
|
|
224
|
-
return StreamlitAppConfig(response=raw_config)
|
|
225
|
-
if callable(raw_config):
|
|
226
|
-
return StreamlitAppConfig(response=raw_config)
|
|
227
|
-
|
|
228
|
-
raise TypeError(
|
|
229
|
-
"APP_CONFIG must be a dict, callable, BaseResponse, or StreamlitAppConfig."
|
|
230
|
-
)
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
def _instantiate_response(candidate: object) -> BaseResponse[BaseStructure]:
|
|
234
|
-
"""Instantiate a :class:`BaseResponse` from the provided candidate.
|
|
235
|
-
|
|
236
|
-
Parameters
|
|
237
|
-
----------
|
|
238
|
-
candidate : object
|
|
239
|
-
Configured response source.
|
|
240
|
-
|
|
241
|
-
Returns
|
|
242
|
-
-------
|
|
243
|
-
BaseResponse[BaseStructure]
|
|
244
|
-
Active response instance.
|
|
245
|
-
|
|
246
|
-
Raises
|
|
247
|
-
------
|
|
248
|
-
TypeError
|
|
249
|
-
If the candidate cannot produce a ``BaseResponse`` instance.
|
|
250
|
-
"""
|
|
251
|
-
if isinstance(candidate, BaseResponse):
|
|
252
|
-
return candidate
|
|
253
|
-
if isinstance(candidate, type) and issubclass(candidate, BaseResponse):
|
|
254
|
-
response_cls = cast(type[BaseResponse[BaseStructure]], candidate)
|
|
255
|
-
return response_cls() # type: ignore[call-arg]
|
|
256
|
-
if callable(candidate):
|
|
257
|
-
response_callable = cast(Callable[[], BaseResponse[BaseStructure]], candidate)
|
|
258
|
-
response = response_callable()
|
|
259
|
-
if isinstance(response, BaseResponse):
|
|
260
|
-
return response
|
|
261
|
-
raise TypeError("response must be a BaseResponse, subclass, or callable")
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
def _config_from_mapping(raw_config: dict) -> StreamlitAppConfig:
|
|
265
|
-
"""Build :class:`StreamlitAppConfig` from a mapping with aliases.
|
|
266
|
-
|
|
267
|
-
The mapping may provide ``build_response`` directly or a ``response`` key
|
|
268
|
-
containing a :class:`BaseResponse` instance, subclass, or callable.
|
|
269
|
-
|
|
270
|
-
Parameters
|
|
271
|
-
----------
|
|
272
|
-
raw_config : dict
|
|
273
|
-
Developer-supplied mapping from the configuration module.
|
|
274
|
-
|
|
275
|
-
Returns
|
|
276
|
-
-------
|
|
277
|
-
StreamlitAppConfig
|
|
278
|
-
Validated configuration derived from ``raw_config``.
|
|
279
|
-
"""
|
|
280
|
-
config_kwargs = dict(raw_config)
|
|
281
|
-
response_candidate = config_kwargs.pop("response", None)
|
|
282
|
-
if response_candidate is None:
|
|
283
|
-
response_candidate = config_kwargs.pop("build_response", None)
|
|
284
|
-
if response_candidate is not None:
|
|
285
|
-
config_kwargs["response"] = response_candidate
|
|
286
|
-
|
|
287
|
-
return StreamlitAppConfig(**config_kwargs)
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
def load_app_config(
|
|
291
|
-
config_path: Path,
|
|
292
|
-
) -> StreamlitAppConfig:
|
|
293
|
-
"""Proxy to :meth:`StreamlitAppConfig.load_app_config` for compatibility."""
|
|
294
|
-
return StreamlitAppConfig.load_app_config(config_path=config_path)
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
def _load_configuration(config_path: Path) -> StreamlitAppConfig:
|
|
298
|
-
"""Load the Streamlit configuration and present user-friendly errors.
|
|
299
|
-
|
|
300
|
-
Parameters
|
|
301
|
-
----------
|
|
302
|
-
config_path : Path
|
|
303
|
-
Filesystem location of the developer-authored configuration module.
|
|
304
|
-
|
|
305
|
-
Returns
|
|
306
|
-
-------
|
|
307
|
-
StreamlitAppConfig
|
|
308
|
-
Validated configuration object.
|
|
309
|
-
"""
|
|
310
|
-
try:
|
|
311
|
-
return StreamlitAppConfig.load_app_config(config_path=config_path)
|
|
312
|
-
except Exception as exc: # pragma: no cover - surfaced in UI
|
|
313
|
-
import streamlit as st # type: ignore[import-not-found]
|
|
314
|
-
|
|
315
|
-
st.error(f"Configuration error: {exc}")
|
|
316
|
-
st.stop()
|
|
317
|
-
raise RuntimeError("Configuration loading halted.") from exc
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
__all__ = [
|
|
321
|
-
"StreamlitAppConfig",
|
|
322
|
-
"load_app_config",
|
|
323
|
-
"_load_configuration",
|
|
324
|
-
]
|
|
@@ -1,194 +0,0 @@
|
|
|
1
|
-
Metadata-Version: 2.4
|
|
2
|
-
Name: openai-sdk-helpers
|
|
3
|
-
Version: 0.0.8
|
|
4
|
-
Summary: Composable helpers for OpenAI SDK agents, prompts, and storage
|
|
5
|
-
Author: openai-sdk-helpers maintainers
|
|
6
|
-
License: MIT
|
|
7
|
-
License-File: LICENSE
|
|
8
|
-
Requires-Python: >=3.10
|
|
9
|
-
Requires-Dist: jinja2
|
|
10
|
-
Requires-Dist: openai
|
|
11
|
-
Requires-Dist: openai-agents
|
|
12
|
-
Requires-Dist: pydantic<3,>=2.7
|
|
13
|
-
Requires-Dist: python-dotenv
|
|
14
|
-
Requires-Dist: streamlit
|
|
15
|
-
Requires-Dist: typing-extensions<5,>=4.15.0
|
|
16
|
-
Description-Content-Type: text/markdown
|
|
17
|
-
|
|
18
|
-
<div align="center">
|
|
19
|
-
|
|
20
|
-
# openai-sdk-helpers
|
|
21
|
-
|
|
22
|
-
Shared primitives for composing OpenAI agent workflows: structures, response
|
|
23
|
-
handling, prompt rendering, and reusable agent factories.
|
|
24
|
-
|
|
25
|
-
</div>
|
|
26
|
-
|
|
27
|
-
## Overview
|
|
28
|
-
|
|
29
|
-
`openai-sdk-helpers` packages the common building blocks required to assemble agent-driven
|
|
30
|
-
applications. The library intentionally focuses on reusable primitives—data
|
|
31
|
-
structures, configuration helpers, and orchestration utilities—while leaving
|
|
32
|
-
application-specific prompts and tools to the consuming project.
|
|
33
|
-
|
|
34
|
-
### Features
|
|
35
|
-
|
|
36
|
-
- **Agent wrappers** for OpenAI Agents SDK with synchronous and asynchronous
|
|
37
|
-
entry points.
|
|
38
|
-
- **Prompt rendering** powered by Jinja for dynamic agent instructions.
|
|
39
|
-
- **Typed structures** for prompts, responses, and search workflows to ensure
|
|
40
|
-
predictable inputs and outputs.
|
|
41
|
-
- **Vector and web search flows** that coordinate planning, execution, and
|
|
42
|
-
reporting.
|
|
43
|
-
- **Reusable text agents** for summarization and translation tasks.
|
|
44
|
-
|
|
45
|
-
## Installation
|
|
46
|
-
|
|
47
|
-
Install the package directly from PyPI to reuse it across projects:
|
|
48
|
-
|
|
49
|
-
```bash
|
|
50
|
-
pip install openai-sdk-helpers
|
|
51
|
-
```
|
|
52
|
-
|
|
53
|
-
Type information ships with the published wheel via `py.typed`, so external
|
|
54
|
-
projects can rely on the bundled annotations without adding custom stubs.
|
|
55
|
-
|
|
56
|
-
For local development, install with editable sources and the optional dev
|
|
57
|
-
dependencies:
|
|
58
|
-
|
|
59
|
-
```bash
|
|
60
|
-
pip install -e .
|
|
61
|
-
pip install -e . --group dev
|
|
62
|
-
```
|
|
63
|
-
|
|
64
|
-
## Quickstart
|
|
65
|
-
|
|
66
|
-
Create a basic vector search workflow by wiring your own prompt templates and
|
|
67
|
-
preferred model configuration:
|
|
68
|
-
|
|
69
|
-
```python
|
|
70
|
-
from pathlib import Path
|
|
71
|
-
|
|
72
|
-
from openai_sdk_helpers.agent.vector_search import VectorSearch
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
prompts = Path("./prompts")
|
|
76
|
-
vector_search = VectorSearch(prompt_dir=prompts, default_model="gpt-4o-mini")
|
|
77
|
-
|
|
78
|
-
report = vector_search.run_agent_sync("Explain quantum entanglement for beginners")
|
|
79
|
-
print(report.report)
|
|
80
|
-
```
|
|
81
|
-
|
|
82
|
-
### Text utilities
|
|
83
|
-
|
|
84
|
-
Use the built-in text helpers when you need lightweight single-step agents.
|
|
85
|
-
|
|
86
|
-
```python
|
|
87
|
-
from openai_sdk_helpers.agent import (
|
|
88
|
-
SummarizerAgent,
|
|
89
|
-
TranslatorAgent,
|
|
90
|
-
ValidatorAgent,
|
|
91
|
-
)
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
summarizer = SummarizerAgent(default_model="gpt-4o-mini")
|
|
95
|
-
translator = TranslatorAgent(default_model="gpt-4o-mini")
|
|
96
|
-
validator = ValidatorAgent(default_model="gpt-4o-mini")
|
|
97
|
-
|
|
98
|
-
summary = summarizer.run_sync("Long-form content to condense")
|
|
99
|
-
translation = translator.run_sync("Bonjour", target_language="English")
|
|
100
|
-
guardrails = validator.run_sync(
|
|
101
|
-
"Share meeting notes with names removed", agent_output=summary.text
|
|
102
|
-
)
|
|
103
|
-
```
|
|
104
|
-
|
|
105
|
-
Prompt templates are optional for the built-in text helpers. They already ship
|
|
106
|
-
with defaults under `src/openai_sdk_helpers/prompt`, so you do **not** need to
|
|
107
|
-
create placeholder files when installing from PyPI. Only pass a `prompt_dir`
|
|
108
|
-
when you have real replacements you want to load.
|
|
109
|
-
|
|
110
|
-
The vector search workflow expects real prompts for each agent (for example,
|
|
111
|
-
`vector_planner.jinja`, `vector_search.jinja`, and `vector_writer.jinja`). If
|
|
112
|
-
you point `prompt_dir` at a folder that does not contain those files, agent
|
|
113
|
-
construction fails with a `FileNotFoundError`. Skip `prompt_dir` entirely unless
|
|
114
|
-
you have working templates ready.
|
|
115
|
-
|
|
116
|
-
### Centralized OpenAI configuration
|
|
117
|
-
|
|
118
|
-
`openai-sdk-helpers` ships with a lightweight `OpenAISettings` helper so projects can share
|
|
119
|
-
consistent authentication, routing, and model defaults when using the OpenAI
|
|
120
|
-
SDK:
|
|
121
|
-
|
|
122
|
-
```python
|
|
123
|
-
from openai_sdk_helpers import OpenAISettings
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
# Load from environment variables or a local .env file
|
|
127
|
-
settings = OpenAISettings.from_env()
|
|
128
|
-
client = settings.create_client()
|
|
129
|
-
|
|
130
|
-
# Reuse the default model across agents
|
|
131
|
-
vector_search = VectorSearch(
|
|
132
|
-
prompt_dir=prompts, default_model=settings.default_model or "gpt-4o-mini"
|
|
133
|
-
)
|
|
134
|
-
```
|
|
135
|
-
|
|
136
|
-
The helper reads `OPENAI_API_KEY`, `OPENAI_ORG_ID`, `OPENAI_PROJECT_ID`,
|
|
137
|
-
`OPENAI_BASE_URL`, `OPENAI_MODEL`, `OPENAI_TIMEOUT`, and `OPENAI_MAX_RETRIES` by
|
|
138
|
-
default but supports overrides for custom deployments. Pass uncommon OpenAI
|
|
139
|
-
client keyword arguments (such as `default_headers`, `http_client`, or
|
|
140
|
-
`base_url` proxies) through `extra_client_kwargs` when instantiating
|
|
141
|
-
`OpenAISettings`.
|
|
142
|
-
|
|
143
|
-
## Development
|
|
144
|
-
|
|
145
|
-
The repository is configured for a lightweight Python development workflow.
|
|
146
|
-
Before opening a pull request, format and validate your changes locally:
|
|
147
|
-
|
|
148
|
-
```bash
|
|
149
|
-
# Style and formatting
|
|
150
|
-
pydocstyle src
|
|
151
|
-
black --check .
|
|
152
|
-
|
|
153
|
-
# Static type checking
|
|
154
|
-
pyright src
|
|
155
|
-
|
|
156
|
-
# Unit tests with coverage
|
|
157
|
-
pytest -q --cov=src --cov-report=term-missing --cov-fail-under=70
|
|
158
|
-
```
|
|
159
|
-
|
|
160
|
-
## Project Structure
|
|
161
|
-
|
|
162
|
-
- `src/openai_sdk_helpers/agent`: Agent factories, orchestration helpers, and search
|
|
163
|
-
workflows.
|
|
164
|
-
- `src/openai_sdk_helpers/prompt`: Prompt rendering utilities backed by Jinja.
|
|
165
|
-
- `src/openai_sdk_helpers/response`: Response parsing and transformation helpers.
|
|
166
|
-
- `src/openai_sdk_helpers/structure`: Typed data structures shared across workflows.
|
|
167
|
-
- `src/openai_sdk_helpers/vector_storage`: Minimal vector store abstraction.
|
|
168
|
-
- `tests/`: Unit tests covering core modules and structures.
|
|
169
|
-
|
|
170
|
-
## Key modules
|
|
171
|
-
|
|
172
|
-
The package centers around a handful of cohesive building blocks:
|
|
173
|
-
|
|
174
|
-
- `openai_sdk_helpers.agent.project_manager.ProjectManager` coordinates prompt
|
|
175
|
-
creation, plan building, task execution, and summarization while persisting
|
|
176
|
-
intermediate artifacts to disk.
|
|
177
|
-
- `openai_sdk_helpers.agent.vector_search.VectorSearch` bundles the planners,
|
|
178
|
-
executors, and summarizers required to run a multi-turn vector search flow
|
|
179
|
-
from a single entry point.
|
|
180
|
-
- `openai_sdk_helpers.agent.summarizer.SummarizerAgent`,
|
|
181
|
-
`agent.translator.TranslatorAgent`, and `agent.validator.ValidatorAgent`
|
|
182
|
-
expose streamlined text-processing utilities that reuse shared prompt
|
|
183
|
-
templates.
|
|
184
|
-
- `openai_sdk_helpers.response` contains the response runners and helpers used
|
|
185
|
-
to normalize outputs from agents, including streaming responses.
|
|
186
|
-
- `openai_sdk_helpers.utils` holds JSON serialization helpers, logging
|
|
187
|
-
utilities, and common validation helpers used across modules.
|
|
188
|
-
|
|
189
|
-
## Contributing
|
|
190
|
-
|
|
191
|
-
Contributions are welcome! Please accompany functional changes with relevant
|
|
192
|
-
tests and ensure all quality gates pass. Follow the NumPy-style docstring
|
|
193
|
-
conventions outlined in `AGENTS.md` to keep the codebase consistent.
|
|
194
|
-
|
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
openai_sdk_helpers/__init__.py,sha256=510VjcPPtGcjEQuhkAswEi7guNFhBHBpaPuuFzAO3RA,1592
|
|
2
|
-
openai_sdk_helpers/config.py,sha256=OH--g7Xp4ftucA2C4o6FCX0M9Z15KMRpkY0lpn0mmOI,6455
|
|
3
|
-
openai_sdk_helpers/environment.py,sha256=t_AFP6OXjRBoIQVZdgjqZzcUWB-FDeYn4KzKn5FgrnY,693
|
|
4
|
-
openai_sdk_helpers/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
5
|
-
openai_sdk_helpers/agent/__init__.py,sha256=1sRtu_TbnKR7EstzZjoi2OUOk0xJOTn4xbo5ZeoPIhk,825
|
|
6
|
-
openai_sdk_helpers/agent/base.py,sha256=P6FYmXssJduFvLaupde0H6lXIe0IJyDZGfEPOHAlMxA,10060
|
|
7
|
-
openai_sdk_helpers/agent/config.py,sha256=IZDF83f_QT-1-3GdTVrn9cQCoaaH4KNcrO-ocfc-LwY,1925
|
|
8
|
-
openai_sdk_helpers/agent/project_manager.py,sha256=uYCZyAG8_Snxef4mv5ax-nI_XVvRPUh43I0pY_AdiiU,16249
|
|
9
|
-
openai_sdk_helpers/agent/prompt_utils.py,sha256=8uCm08YuJ94rKgBuIkio2O4EpbwDmTXNfgeddbih8JA,228
|
|
10
|
-
openai_sdk_helpers/agent/runner.py,sha256=-hd_k4h2mmKDpocIIQWQs_5Y9wvq7cLTopmNMwwz3Jc,5375
|
|
11
|
-
openai_sdk_helpers/agent/summarizer.py,sha256=lijBOL7vE7pm4ShquB-j6zJKLmw0X94KAY0zDC6RkD4,2444
|
|
12
|
-
openai_sdk_helpers/agent/translator.py,sha256=Cj3eJ2IakX2UqSeDotgqpbmM89FekpYt3GglM8Qxglw,4229
|
|
13
|
-
openai_sdk_helpers/agent/utils.py,sha256=DTD5foCqGYfXf13F2bZMYIQROl7SbDSy5GDPGi0Zl-0,1089
|
|
14
|
-
openai_sdk_helpers/agent/validation.py,sha256=omKfbClYdPQxxn9WKlw33s42AkudeFw54DmgGSe2UhQ,3216
|
|
15
|
-
openai_sdk_helpers/agent/vector_search.py,sha256=pf_kIFl_TK4ZXvTcZzNqXxZuyq4QfF4ncDluAp4nj0c,15529
|
|
16
|
-
openai_sdk_helpers/agent/web_search.py,sha256=mAtUoXSULn5p1Et6XrGptdZHBlBPNMXnSaTx8pSRsfs,12155
|
|
17
|
-
openai_sdk_helpers/enums/__init__.py,sha256=HhzM9YVDqPijpnKzA-qnzbX62104FrGDcnN-cEYMD_w,149
|
|
18
|
-
openai_sdk_helpers/enums/base.py,sha256=dBrzbIA3Ft2Jy-1PhMImEQeDwH0FXIMGHdg68DsG7WE,697
|
|
19
|
-
openai_sdk_helpers/prompt/__init__.py,sha256=Pio9s99ej0ior5gKr8m-hSUgqkBOgFdNu1xofvjPEf8,2275
|
|
20
|
-
openai_sdk_helpers/prompt/summarizer.jinja,sha256=jliSetWDISbql1EkWi1RB8-L_BXUg8JMkRRsPRHuzbY,309
|
|
21
|
-
openai_sdk_helpers/prompt/translator.jinja,sha256=SZhW8ipEzM-9IA4wyS_r2wIMTAclWrilmk1s46njoL0,291
|
|
22
|
-
openai_sdk_helpers/prompt/validator.jinja,sha256=6t8q_IdxFd3mVBGX6SFKNOert1Wo3YpTOji2SNEbbtE,547
|
|
23
|
-
openai_sdk_helpers/response/__init__.py,sha256=TSTewIzMyAkR7kcxZlZ7-v3KXpDD2JBC6xG3eYa67zQ,505
|
|
24
|
-
openai_sdk_helpers/response/base.py,sha256=tCWRcBhNIRUz77HWxHRdCPFuywbUKCYa7ac-TvxNWiI,22593
|
|
25
|
-
openai_sdk_helpers/response/messages.py,sha256=O6c2E8Q6cm1nE4McPevvqcxa4kUFd5pL2MuUHtOVqsY,7917
|
|
26
|
-
openai_sdk_helpers/response/runner.py,sha256=xCiZ1-1kGLmVuDzX31zrx7snNrbQfn7OS-BYN-XG0es,2536
|
|
27
|
-
openai_sdk_helpers/response/tool_call.py,sha256=5ZZLyblNe35kRZ3_0JgGASS92nlT2xAxvCsncAss_xg,2960
|
|
28
|
-
openai_sdk_helpers/response/vector_store.py,sha256=T1xiev85xv0C9f5t25ss8HUfir0c9zLPwXk3C1qAel0,2418
|
|
29
|
-
openai_sdk_helpers/streamlit_app/__init__.py,sha256=RNcbMPaIERdFQ4wh_td3EjS6cJ_72eMBP-Ti7SVeiwY,261
|
|
30
|
-
openai_sdk_helpers/streamlit_app/app.py,sha256=o-0Zh9lR_-ubOQX79sfA-6rFxdxhGWlRzOazmECxomE,8066
|
|
31
|
-
openai_sdk_helpers/streamlit_app/configuration.py,sha256=KUo4E1yTSyuI9MV17Lw8_FP6OhEqS-zv2HdsGk9bCQA,10340
|
|
32
|
-
openai_sdk_helpers/streamlit_app/streamlit_web_search.py,sha256=1eUCYFh0b_LnWb6HSBMztt1h92TF3fTW_InUNMOPkG8,2480
|
|
33
|
-
openai_sdk_helpers/structure/__init__.py,sha256=GBD48p3M9wnOPmEO9t9t5XuiMQedmDBClKmjDLEjcUo,1129
|
|
34
|
-
openai_sdk_helpers/structure/agent_blueprint.py,sha256=opL-dER3a_f_JWC3Jx9ovRdbC4XZe9X20-o1YUq9sgw,7569
|
|
35
|
-
openai_sdk_helpers/structure/base.py,sha256=0OZao5cenz52AKoMLjLO8f_it_5Nm38FPvO8GGyMzNA,24170
|
|
36
|
-
openai_sdk_helpers/structure/prompt.py,sha256=Yovho9WA1AZP1FhKBieBpVThrUn62g4k40mxNrBoY9s,582
|
|
37
|
-
openai_sdk_helpers/structure/responses.py,sha256=KivhRltUlrK8ey9Tk9rDNceHb7uC2gNE38iQJXFOxug,3507
|
|
38
|
-
openai_sdk_helpers/structure/summary.py,sha256=zYRKuBjZHz0GvLRofvJdfD9u101xKgVhFc5CZIlscUE,1682
|
|
39
|
-
openai_sdk_helpers/structure/validation.py,sha256=IdlPb3I1PdCah7kciE8iDRZy_ltk5GSXQyRJUufz7K0,1405
|
|
40
|
-
openai_sdk_helpers/structure/vector_search.py,sha256=M3TQwxOg9mJmZcLgx7UhZkclnbdcH2K_N-XxUU9Eoxo,2457
|
|
41
|
-
openai_sdk_helpers/structure/web_search.py,sha256=6RA0gS8tAe_8zBMA1IS-YLNoGzLFmvS0YG0OwfUGo7Y,1496
|
|
42
|
-
openai_sdk_helpers/structure/plan/__init__.py,sha256=OVTGp0MAb8RLjE7TZk5zoXjXIih7zzfwPYIyO7CCwVM,261
|
|
43
|
-
openai_sdk_helpers/structure/plan/enum.py,sha256=EYGdUckSUSOXQCTIbD8RhSQNylgVTVvOnb7za6fv6_A,1772
|
|
44
|
-
openai_sdk_helpers/structure/plan/plan.py,sha256=33qBu-yzFEpYHVsvGiGMsdZphYpOD7eT5AjNQzt5cmo,7480
|
|
45
|
-
openai_sdk_helpers/structure/plan/task.py,sha256=Qn-GXV0VuOYA-EHXSC6tQlcXObKMeV3-TQhgeepl2L8,3481
|
|
46
|
-
openai_sdk_helpers/utils/__init__.py,sha256=54_AalcYtv3cgkg86yvHLe2cVuSEYizehf6arv37JJQ,507
|
|
47
|
-
openai_sdk_helpers/utils/core.py,sha256=1Q8zaOkuorbj3tYcbM0iIjhURKJpD0xl6rEaXjI-080,9132
|
|
48
|
-
openai_sdk_helpers/vector_storage/__init__.py,sha256=BjUueFnxmF4T6YOCra2nqa8rEAzsihEYWavkYB7S_lM,384
|
|
49
|
-
openai_sdk_helpers/vector_storage/cleanup.py,sha256=6e_A9MAOKhJl_9EbRgGiB0NrrN79IwN0mMnHrwp4gd8,2964
|
|
50
|
-
openai_sdk_helpers/vector_storage/storage.py,sha256=alOetHIJUrZ6hjP3Q_3A-g5ROraw7FXJOWhOSdNorOA,19345
|
|
51
|
-
openai_sdk_helpers/vector_storage/types.py,sha256=9u5oBxKTDf_ljvbWhp1dWVW1zrlVwLd4OpikygvlKJI,1298
|
|
52
|
-
openai_sdk_helpers-0.0.8.dist-info/METADATA,sha256=OWSkOhsK10d3ko-ItS9O47OTtJDDS6QUgIGiBvXeKFg,6582
|
|
53
|
-
openai_sdk_helpers-0.0.8.dist-info/WHEEL,sha256=WLgqFyCfm_KASv4WHyYy0P3pM_m7J5L9k2skdKLirC8,87
|
|
54
|
-
openai_sdk_helpers-0.0.8.dist-info/licenses/LICENSE,sha256=CUhc1NrE50bs45tcXF7OcTQBKEvkUuLqeOHgrWQ5jaA,1067
|
|
55
|
-
openai_sdk_helpers-0.0.8.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|