ostruct-cli 0.8.3__py3-none-any.whl → 0.8.4__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.
- ostruct/cli/cli.py +4 -0
- ostruct/cli/click_options.py +2 -8
- ostruct/cli/runner.py +15 -15
- {ostruct_cli-0.8.3.dist-info → ostruct_cli-0.8.4.dist-info}/METADATA +9 -1
- {ostruct_cli-0.8.3.dist-info → ostruct_cli-0.8.4.dist-info}/RECORD +8 -8
- {ostruct_cli-0.8.3.dist-info → ostruct_cli-0.8.4.dist-info}/LICENSE +0 -0
- {ostruct_cli-0.8.3.dist-info → ostruct_cli-0.8.4.dist-info}/WHEEL +0 -0
- {ostruct_cli-0.8.3.dist-info → ostruct_cli-0.8.4.dist-info}/entry_points.txt +0 -0
ostruct/cli/cli.py
CHANGED
@@ -4,6 +4,7 @@ import sys
|
|
4
4
|
from typing import Optional
|
5
5
|
|
6
6
|
import click
|
7
|
+
from dotenv import load_dotenv
|
7
8
|
|
8
9
|
from .. import __version__
|
9
10
|
from .commands import create_command_group
|
@@ -107,6 +108,9 @@ def create_cli() -> click.Command:
|
|
107
108
|
|
108
109
|
def main() -> None:
|
109
110
|
"""Main entry point for the CLI."""
|
111
|
+
# Load environment variables from .env file
|
112
|
+
load_dotenv()
|
113
|
+
|
110
114
|
try:
|
111
115
|
cli(standalone_mode=False)
|
112
116
|
except (
|
ostruct/cli/click_options.py
CHANGED
@@ -492,12 +492,13 @@ def api_options(f: Union[Command, Callable[..., Any]]) -> Command:
|
|
492
492
|
environment variable.""",
|
493
493
|
)(cmd)
|
494
494
|
|
495
|
+
# API timeout for OpenAI calls
|
495
496
|
cmd = click.option(
|
496
497
|
"--timeout",
|
497
498
|
type=click.FloatRange(1.0, None),
|
498
499
|
default=60.0,
|
499
500
|
show_default=True,
|
500
|
-
help="
|
501
|
+
help="Timeout in seconds for OpenAI API calls.",
|
501
502
|
)(cmd)
|
502
503
|
|
503
504
|
return cast(Command, cmd)
|
@@ -854,13 +855,6 @@ def debug_progress_options(f: Union[Command, Callable[..., Any]]) -> Command:
|
|
854
855
|
"--verbose", is_flag=True, help="Enable verbose logging"
|
855
856
|
)(cmd)
|
856
857
|
|
857
|
-
cmd = click.option(
|
858
|
-
"--timeout",
|
859
|
-
type=int,
|
860
|
-
default=3600,
|
861
|
-
help="Operation timeout in seconds (default: 3600 = 1 hour)",
|
862
|
-
)(cmd)
|
863
|
-
|
864
858
|
return cast(Command, cmd)
|
865
859
|
|
866
860
|
|
ostruct/cli/runner.py
CHANGED
@@ -33,9 +33,6 @@ from .sentinel import extract_json_block
|
|
33
33
|
from .serialization import LogSerializer
|
34
34
|
from .services import ServiceContainer
|
35
35
|
from .types import CLIParams
|
36
|
-
from .unattended_operation import (
|
37
|
-
UnattendedOperationManager,
|
38
|
-
)
|
39
36
|
|
40
37
|
|
41
38
|
# Error classes for API operations
|
@@ -855,10 +852,6 @@ async def execute_model(
|
|
855
852
|
"""Execute the model with the given parameters."""
|
856
853
|
logger.debug("=== Execution Phase ===")
|
857
854
|
|
858
|
-
# Initialize unattended operation manager
|
859
|
-
timeout_seconds = int(args.get("timeout", 3600))
|
860
|
-
operation_manager = UnattendedOperationManager(timeout_seconds)
|
861
|
-
|
862
855
|
# Pre-validate unattended compatibility
|
863
856
|
# Note: MCP validation is handled during MCP configuration processing
|
864
857
|
# mcp_servers = args.get("mcp_servers", [])
|
@@ -874,12 +867,22 @@ async def execute_model(
|
|
874
867
|
|
875
868
|
api_key = args.get("api_key") or os.getenv("OPENAI_API_KEY")
|
876
869
|
if not api_key:
|
877
|
-
msg =
|
870
|
+
msg = (
|
871
|
+
"No OpenAI API key found. Please:\n"
|
872
|
+
" • Set OPENAI_API_KEY environment variable, or\n"
|
873
|
+
" • Create a .env file with OPENAI_API_KEY=your-key-here, or\n"
|
874
|
+
" • Use --api-key option (not recommended for production)\n"
|
875
|
+
"\n"
|
876
|
+
"Get your API key from: https://platform.openai.com/api-keys"
|
877
|
+
)
|
878
878
|
logger.error(msg)
|
879
879
|
raise CLIError(msg, exit_code=ExitCode.API_ERROR)
|
880
880
|
|
881
|
+
# Get API timeout
|
882
|
+
api_timeout = args.get("timeout", 60.0)
|
881
883
|
client = AsyncOpenAI(
|
882
|
-
api_key=api_key,
|
884
|
+
api_key=api_key,
|
885
|
+
timeout=min(float(api_timeout), 300.0),
|
883
886
|
) # Cap at 5 min for client timeout
|
884
887
|
|
885
888
|
# Create service container for dependency management
|
@@ -1352,13 +1355,10 @@ async def execute_model(
|
|
1352
1355
|
|
1353
1356
|
return ExitCode.SUCCESS
|
1354
1357
|
|
1355
|
-
# Execute main operation
|
1358
|
+
# Execute main operation
|
1356
1359
|
try:
|
1357
|
-
result = await
|
1358
|
-
|
1359
|
-
)
|
1360
|
-
# The result should be an ExitCode from execute_main_operation
|
1361
|
-
return result # type: ignore[no-any-return]
|
1360
|
+
result = await execute_main_operation()
|
1361
|
+
return result
|
1362
1362
|
except (
|
1363
1363
|
APIResponseError,
|
1364
1364
|
EmptyResponseError,
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.3
|
2
2
|
Name: ostruct-cli
|
3
|
-
Version: 0.8.
|
3
|
+
Version: 0.8.4
|
4
4
|
Summary: CLI for OpenAI Structured Output with Multi-Tool Integration
|
5
5
|
Author: Yaniv Golan
|
6
6
|
Author-email: yaniv@golan.name
|
@@ -39,6 +39,7 @@ Requires-Dist: pytest (>=8.3.4,<9.0) ; extra == "dev"
|
|
39
39
|
Requires-Dist: pytest-asyncio (>=0.25.2,<1.0) ; extra == "dev"
|
40
40
|
Requires-Dist: pytest-mock (>=3.14.0,<4.0) ; extra == "dev"
|
41
41
|
Requires-Dist: pytest-rerunfailures (>=12.0,<13.0) ; extra == "dev"
|
42
|
+
Requires-Dist: python-dotenv (>=1.0.1,<2.0)
|
42
43
|
Requires-Dist: python-dotenv (>=1.0.1,<2.0) ; extra == "dev"
|
43
44
|
Requires-Dist: pyyaml (>=6.0.2,<7.0)
|
44
45
|
Requires-Dist: sphinx (>=7.0,<8.0) ; extra == "dev"
|
@@ -48,6 +49,7 @@ Requires-Dist: sphinx-rtd-theme (>=1.0,<2.0) ; extra == "docs"
|
|
48
49
|
Requires-Dist: tenacity (>=8.2.3,<9.0) ; extra == "examples"
|
49
50
|
Requires-Dist: tiktoken (==0.9.0)
|
50
51
|
Requires-Dist: tomli (>=2.0.1,<3.0) ; (python_version < "3.11") and (extra == "docs")
|
52
|
+
Requires-Dist: tomli (>=2.0.1,<3.0) ; extra == "dev"
|
51
53
|
Requires-Dist: tomli (>=2.0.1,<3.0) ; python_version < "3.11"
|
52
54
|
Requires-Dist: twine (>=6.0.1,<7.0) ; extra == "dev"
|
53
55
|
Requires-Dist: types-cachetools (>=5.5.0.20240820) ; extra == "dev"
|
@@ -237,6 +239,8 @@ ostruct-cli respects the following environment variables:
|
|
237
239
|
- `OSTRUCT_DISABLE_REGISTRY_UPDATE_CHECKS`: Set to "1", "true", or "yes" to disable automatic registry update checks
|
238
240
|
- `MCP_<NAME>_URL`: Custom MCP server URLs (e.g., `MCP_STRIPE_URL=https://mcp.stripe.com`)
|
239
241
|
|
242
|
+
**💡 Tip**: ostruct automatically loads `.env` files from the current directory. Environment variables take precedence over `.env` file values.
|
243
|
+
|
240
244
|
<details>
|
241
245
|
<summary><strong>Shell Completion Setup</strong> (Click to expand)</summary>
|
242
246
|
|
@@ -427,7 +431,11 @@ tools:
|
|
427
431
|
1. Set your OpenAI API key:
|
428
432
|
|
429
433
|
```bash
|
434
|
+
# Environment variable
|
430
435
|
export OPENAI_API_KEY=your-api-key
|
436
|
+
|
437
|
+
# Or create a .env file
|
438
|
+
echo 'OPENAI_API_KEY=your-api-key' > .env
|
431
439
|
```
|
432
440
|
|
433
441
|
### Example 1: Basic Text Extraction (Simplest)
|
@@ -2,8 +2,8 @@ ostruct/__init__.py,sha256=X6zo6V7ZNMv731Wi388aTVQngD1410ExGwGx4J6lpyo,187
|
|
2
2
|
ostruct/cli/__init__.py,sha256=e-DtWRviCr3fIAJH4cB4UAvles3-rqnhJaTOlBn9TKs,871
|
3
3
|
ostruct/cli/base_errors.py,sha256=o-877bJJA8yJWISRPy0KyL6wDu1-_avddmQIfVePuFM,5989
|
4
4
|
ostruct/cli/cache_manager.py,sha256=ej3KrRfkKKZ_lEp2JswjbJ5bW2ncsvna9NeJu81cqqs,5192
|
5
|
-
ostruct/cli/cli.py,sha256=
|
6
|
-
ostruct/cli/click_options.py,sha256=
|
5
|
+
ostruct/cli/cli.py,sha256=pzOzKMvWQMRS1I9w4raAUi-O7IN6OKViNTcOeJGEqhI,4196
|
6
|
+
ostruct/cli/click_options.py,sha256=UWLBIkfVMXcIMXInJFWNYNO9Ieg8YrJEzRfkKungy48,31730
|
7
7
|
ostruct/cli/code_interpreter.py,sha256=lnnyEvUh2pGObN9ENpr-X4p0C0oIWiyG1CFQWW4akBQ,16726
|
8
8
|
ostruct/cli/commands/__init__.py,sha256=3NHz-WZ9XqrnWWMksoV2MpYpHnjA-EO9lsrBOYeHcjY,723
|
9
9
|
ostruct/cli/commands/list_models.py,sha256=yeuQpUGAmRr4uOHS7teuVHkC9dkqN0yKDOEw_n-ehi0,4662
|
@@ -28,7 +28,7 @@ ostruct/cli/path_utils.py,sha256=j44q1OoLkqMErgK-qEuhuIZ1VyzqRIvNgxR1et9PoXA,481
|
|
28
28
|
ostruct/cli/progress.py,sha256=rj9nVEco5UeZORMbzd7mFJpFGJjbH9KbBFh5oTE5Anw,3415
|
29
29
|
ostruct/cli/progress_reporting.py,sha256=MBjALM4pmPd_d9YuXqH162-tkC6DDKYmz-pJPSGLTfk,13669
|
30
30
|
ostruct/cli/registry_updates.py,sha256=ohiHdlfrocvThpR_ZjMyqulDKFjRM1hIFKOlNzpaqHg,5138
|
31
|
-
ostruct/cli/runner.py,sha256=
|
31
|
+
ostruct/cli/runner.py,sha256=GzCsPiwhxiaoXvCv-ykFO8KucMvGRyIOPuaNMCVF1pw,65107
|
32
32
|
ostruct/cli/schema_utils.py,sha256=9LnsjxEKg6RIfXQB3nS3pyDggm5n-4-thXf92897gJU,3590
|
33
33
|
ostruct/cli/schema_validation.py,sha256=ohEuxJ0KF93qphj0JSZDnrxDn0C2ZU37g-U2JY03onM,8154
|
34
34
|
ostruct/cli/security/__init__.py,sha256=CQpkCgTFYlA1p6atpQeNgIKtE4LZGUKt4EbytbGKpCs,846
|
@@ -64,8 +64,8 @@ ostruct/cli/unattended_operation.py,sha256=kI95SSVJC_taxORXQYrce_qLEnuKc6edwn9tM
|
|
64
64
|
ostruct/cli/utils.py,sha256=uY7c0NaINHWfnl77FcPE3TmYUXv3RqEeUTjrCMDij9A,922
|
65
65
|
ostruct/cli/validators.py,sha256=lbxAUUVS5TPJ7HdYZ5yB7gUjJqfcClZCuh0oktoq0E0,15291
|
66
66
|
ostruct/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
67
|
-
ostruct_cli-0.8.
|
68
|
-
ostruct_cli-0.8.
|
69
|
-
ostruct_cli-0.8.
|
70
|
-
ostruct_cli-0.8.
|
71
|
-
ostruct_cli-0.8.
|
67
|
+
ostruct_cli-0.8.4.dist-info/LICENSE,sha256=DmGAkaYzhrdzTB9Y2Rvfzd3mJiF9ZrTOhxN8t6wrfHA,1098
|
68
|
+
ostruct_cli-0.8.4.dist-info/METADATA,sha256=4B4H-EqZAyVZOTzeWH_BZbaDqshFZ8YZvvPpVzzaBx0,25161
|
69
|
+
ostruct_cli-0.8.4.dist-info/WHEEL,sha256=b4K_helf-jlQoXBBETfwnf4B04YC67LOev0jo4fX5m8,88
|
70
|
+
ostruct_cli-0.8.4.dist-info/entry_points.txt,sha256=NFq9IuqHVTem0j9zKjV8C1si_zGcP1RL6Wbvt9fUDXw,48
|
71
|
+
ostruct_cli-0.8.4.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|