sageai


Namesageai JSON
Version 1.0.5 PyPI version JSON
download
home_page
SummaryFile-based functions for ChatGPT's function calling with Pydantic support
upload_time2023-11-15 16:24:59
maintainer
docs_urlNone
authorJUNIORCO
requires_python>=3.9,<3.12
licenseMIT
keywords python openai functions chatgpt gpt4 genai function-calling
VCS
bugtrack_url
requirements No requirements were recorded.
Travis-CI No Travis.
coveralls test coverage No coveralls.
            ![Logo](https://github.com/0xnenlabs/SageAI/assets/45445790/750fb3f9-0830-4948-9a86-61e59d933b45)

<p align="center">
    <em>Folder-based functions for ChatGPT's function calling with Pydantic support 🚀</em>
</p>

<p align="center">
<a href="https://pypi.org/project/sageai" target="_blank">
    <img src="https://img.shields.io/pypi/v/sageai?color=%2334D058&label=pypi%20package" alt="Package version">
</a>
<a href="https://pypi.org/project/sageai" target="_blank">
    <img src="https://img.shields.io/pypi/pyversions/sageai.svg?color=%2334D058" alt="Supported Python versions">
</a>
</p>

SageAI lets you connect custom Python functions to ChatGPT. It organizes these functions in folders
and allows you to call them with natural language.

## Table of Contents

- [Key Features](#key-features)
- [Requirements](#requirements)
- [Installation](#installation)
- [Design](#design)
- [Setup](#setup)
- [Convention](#convention)
- [API](#api)
  - [SageAI Initialize](#sageai-initialize)
  - [SageAI Methods](#sageai-methods)
  - [Vector DB](#vector-db)
- [Testing](#testing)
  - [Unit Tests](#unit-tests)
  - [Integration Tests](#integration-tests)
  - [Output Equality](#output-equality)
  - [CLI](#cli)
- [Examples](#examples)
- [Roadmap](#roadmap)
- [Contributing](#contributing)

## Key Features

- Function organization through folder-centric functions.
- Strong typing for functions using Pydantic.
- Built-in Qdrant vector database with in-memory support for function storage and retrieval, with the option to
  integrate your own.
- Easily test each function with an associated `test.json` file, supporting both unit and integration tests.
- Built with CI/CD in mind, ensuring synchronicity between your vector db and the functions directory across all
  environments using the `index` method.
- Lightweight implementation with only three dependencies:
  - `openai`
  - `pydantic`
  - `qdrant-client`

## Requirements

```
python >=3.9, <3.12
pydantic >=1.6, <=1.10.12
openai >=0.27.0
qdrant-client >=1.4.0
```

## Installation

```bash
# pip
$ pip install sageai

# poetry
$ poetry add sageai
```

## Design

![Design](https://github.com/0xnenlabs/SageAI/assets/45445790/eb81d280-5b69-472a-b45a-4a9275fcf341)

SageAI is built around the concept of a `functions` directory, which contains all of your functions. Each function is
defined in a Python file `function.py`, and is associated with an optional `test.json` file for testing.

The format of the `function.py` file must contain two things in order for SageAI to work:

1. The function itself
2. The `Function` object

Input and output types may be defined using Pydantic models, and are automatically validated by SageAI. They can also be
defined outside the `function.py` file, and imported into the file.

Here is a simplified example of how SageAI might handle a function that fetches the current weather for a given
location.

```python
# functions/get_current_weather/function.py
from enum import Enum
from typing import Optional

from pydantic import BaseModel, Field

from sageai.types.function import Function


class UnitTypes(str, Enum):
    CELSIUS = "Celsius"
    FAHRENHEIT = "Fahrenheit"


class FunctionInput(BaseModel):
    location: str = Field(
        ..., description="The city, e.g. San Francisco"
    )
    unit: Optional[UnitTypes] = Field(
        UnitTypes.CELSIUS, description="The unit of temperature."
    )


class FunctionOutput(BaseModel):
    weather: str

    def __eq__(self, other):
        if not isinstance(other, FunctionOutput):
            return False
        return self.weather == other.weather


def get_current_weather(params: FunctionInput) -> FunctionOutput:
    weather = (
        f"The weather in {params.location} is currently 22 degrees {params.unit.value}."
    )
    return FunctionOutput(weather=weather)


function = Function(
    function=get_current_weather,
    description="Get the current weather in a given location.",
)
```

We'll break down the above example into its components below.

## Setup

Create a `functions` directory in the root directory, and add your functions as described in [Design](#design).

Then initialize `SageAI`.

```python
from sageai import SageAI

sage = SageAI(openai_key="")
```

Then index the vector database.

```python
sage.index()
```

That's it! You're now set up and ready to interact with SageAI through natural language queries. 🚀

```python
message = "What's the weather like in Toronto right now?"
response = sage.chat(
    messages=[dict(role="user", content=message)],
    model="gpt-3.5-turbo-0613",
    top_n=5,
)
# response:
# {
#   'name': 'get_current_weather',
#   'args': {'location': 'Toronto'},
#   'result': {'weather': 'The weather in Toronto is currently 22 degrees Celsius.'}
# }
```

## Convention

SageAI follows a convention over configuration approach to make it easy to define functions.

Ensure that your `function.py` file contains the following:

1. A `function` object that is an instance of `Function`.
2. A function that is the actual function that will be called by ChatGPT.
3. The function **must** have typed input and output Pydantic models.
4. Each field in the input model **must** have a description.

Minimal example:

```python
def my_function(params: PydanticInput) -> PydanticOutput:
    return PydanticOutput(...)


function = Function(
    function=my_function,
    description="My function description.",
)
```

## API

### SageAI Initialize

The `SageAI` constructor accepts the following parameters:

| Parameter               | Description                                                                 | Defaults                 |
| ----------------------- | --------------------------------------------------------------------------- | ------------------------ |
| **openai_key**          | The API key for OpenAI.                                                     | _Required_               |
| **functions_directory** | Directory containing functions.                                             | `/functions`             |
| **vectordb**            | An implementation of the `AbstractVectorDB` for vector database operations. | `DefaultVectorDBService` |
| **log_level**           | Desired log level for the operations.                                       | `ERROR`                  |

### SageAI Methods

#### 1. `chat`

Initiate a chat using OpenAI's API and the provided parameters.

**Parameters**:

| Parameter | Description                                                                                                         | Defaults   |
| --------- | ------------------------------------------------------------------------------------------------------------------- | ---------- |
| -         | Accepts the same parameters as OpenAI's [chat endpoint](https://platform.openai.com/docs/api-reference/chat/create) | -          |
| **top_n** | The number of top functions to consider from the vector database.                                                   | _Required_ |

**Returns**:

```python
dict(
    name="function_name",
    args={"arg1": "value1", "arg2": "value2"},
    result={"out1": "value1", "out2": "value2"},  # Optional
    error="",  # Optional
)
```

> Either `result` or `error` will be present in the response, but not both.

---

#### 2. `get_top_n_functions`

Get the top `n` functions from the vector database based on a query.

**Parameters**:

| Parameter | Description                        | Defaults   |
| --------- | ---------------------------------- | ---------- |
| **query** | The query to search against.       | _Required_ |
| **top_n** | The number of functions to return. | _Required_ |

**Returns**:

- A dict of function names to `Function` definitions.

---

#### 3. `run_function`

Execute a function based on its name and provided arguments.

**Parameters**:

| Parameter | Description                        | Defaults   |
| --------- | ---------------------------------- | ---------- |
| **name**  | Name of the function.              | _Required_ |
| **args**  | Arguments to pass to the function. | _Required_ |

**Returns**:

- The function result as a dict.

---

#### 4. `call_openai`

Calls the OpenAI API with the provided parameters.

**Parameters**:

| Parameter         | Description                                                                                                         | Defaults   |
| ----------------- | ------------------------------------------------------------------------------------------------------------------- | ---------- |
| **openai_args**   | Accepts the same parameters as OpenAI's [chat endpoint](https://platform.openai.com/docs/api-reference/chat/create) | _Required_ |
| **top_functions** | List of dicts that is a representation of your functions.                                                           | _Required_ |

**Returns**:

- A tuple of the function name and the function args.

---

#### 5. `index`

Index the vector database based on the functions directory.
This method is useful to update the vectordb when new functions are added or existing ones are updated.

---

Want more control?

> The `chat` function uses `get_top_n_functions`, `run_function`, and `call_openai` internally.
> However, we also expose these methods incase you wish to use them directly to implement your own `chat` logic.

---

### Vector DB

SageAI comes with a built-in in-memory vector database, Qdrant, which is used to store and retrieve functions.

If you wish to use your own vector database, you can implement the `AbstractVectorDB` class and pass it into the
`SageAI` constructor.

See the [advanced example](/examples/advanced) for an example of how to integrate your own vector database.

## Testing

As for the optional `test.json` file in each function, follow this structure:

```json
[
  {
    "message": "What's the weather like in Toronto right now?",
    "input": {
      "location": "Toronto",
      "unit": "Celsius"
    },
    "output": {
      "weather": "The weather in Toronto is currently 22 degrees Celsius."
    }
  }
]
```

- Each object in the array represents a test case.
- The `message` field is the natural language message that will be sent
  to ChatGPT, and the `input` field is the expected input that will be passed to the function.
- The `output` field is the
  expected output of the function.

SageAI offers unit and integration tests.

---

### Unit Tests

> Unit tests do not call the vector database nor ChatGPT, and **will not** cost you money.

- Unit tests are used to ensure your functions directory is valid, and it tests the function in isolation.
- It tests whether:
  - the `functions` directory exists.
  - each function has a `function.py` file.
  - each `function.py` file has a `Function` object.
  - and more!
- It also tests whether the input and output types are valid, and whether the function returns the expected output based
  on
  the input alone by calling `func(test_case["input"]) == test_case["output"]`.

---

### Integration Tests

> Integration tests will call the vector database and ChatGPT, and **will** cost you money.

- Integration tests are used to test the function by calling ChatGPT and the vector database.
- They test whether the vector database is able to retrieve the function, and whether ChatGPT can call the function
  with the given input and return the expected output.

> Because ChatGPT's responses can vary, integration tests may return different results each time.
> It's important to use integration tests as a tool to ensure ChatGPT is able to call the right function with the right
> input, and not as a definitive test to measure the test rate of your functions.

---

### Output Equality

You can customize how to determine equality between the expected and actual output by overriding the `__eq__`
method in the output model.

```python
class FunctionOutput(BaseModel):
    weather: str
    temperature: int

    def __eq__(self, other):
        if not isinstance(other, FunctionOutput):
            return False
        return self.weather == other.weather
```

In the case above, we only care about the `weather` field, and not the `temperature` field. Therefore, we only compare
the `weather` field in the `__eq__` method.

This is especially useful when you are returning an object from a database, for example, and you only care to test
against a subset of the fields (for example, the `id` field).

---

### CLI

```bash
# To run unit and integration tests for all functions:
poetry run sageai-tests --apikey=openapikey --directory=path/to/functions

# To run unit tests only for all functions:
poetry run sageai-tests --apikey=openapikey --directory=path/to/functions --unit

# To run integration tests only for all functions:
poetry run sageai-tests --apikey=openapikey --directory=path/to/functions --integration

# To run unit and integration tests for a specific function:
poetry run sageai-tests --apikey=openapikey --directory=path/to/functions/get_current_weather
```

| Parameter         | Description                                                   | Defaults     |
| ----------------- | ------------------------------------------------------------- | ------------ |
| **--apikey**      | OpenAI API key.                                               | _Required_   |
| **--directory**   | Directory of the functions or of the specific function to run | _/functions_ |
| **--unit**        | Only run unit tests                                           | false        |
| **--integration** | Only run integration tests                                    | false        |

## Examples

1. [Basic](/examples/basic) - Get started with a simple SageAI function.
2. [Advanced](/examples/advanced) - Dive deeper with more intricate functionalities and use-cases.

## Roadmap

- [ ] Add tests and code coverage
- [ ] Support multiple function calls
- [ ] Support streaming
- [ ] Support asyncio
- [ ] Support Pydantic V2
- [ ] Write Chainlit example
- [ ] Write fullstack example

## Contributing

Interested in contributing to SageAI? Please see our [CONTRIBUTING.md](/CONTRIBUTING.md) for guidelines, coding
standards, and other details.

            

Raw data

            {
    "_id": null,
    "home_page": "",
    "name": "sageai",
    "maintainer": "",
    "docs_url": null,
    "requires_python": ">=3.9,<3.12",
    "maintainer_email": "",
    "keywords": "python,openai,functions,chatgpt,gpt4,genai,function-calling",
    "author": "JUNIORCO",
    "author_email": "sami@lasso.gg",
    "download_url": "https://files.pythonhosted.org/packages/20/64/9fa5fa6596cfbf46c5302056632a0df547e1f6e183dd692b8ff991e0e866/sageai-1.0.5.tar.gz",
    "platform": null,
    "description": "![Logo](https://github.com/0xnenlabs/SageAI/assets/45445790/750fb3f9-0830-4948-9a86-61e59d933b45)\n\n<p align=\"center\">\n    <em>Folder-based functions for ChatGPT's function calling with Pydantic support \ud83d\ude80</em>\n</p>\n\n<p align=\"center\">\n<a href=\"https://pypi.org/project/sageai\" target=\"_blank\">\n    <img src=\"https://img.shields.io/pypi/v/sageai?color=%2334D058&label=pypi%20package\" alt=\"Package version\">\n</a>\n<a href=\"https://pypi.org/project/sageai\" target=\"_blank\">\n    <img src=\"https://img.shields.io/pypi/pyversions/sageai.svg?color=%2334D058\" alt=\"Supported Python versions\">\n</a>\n</p>\n\nSageAI lets you connect custom Python functions to ChatGPT. It organizes these functions in folders\nand allows you to call them with natural language.\n\n## Table of Contents\n\n- [Key Features](#key-features)\n- [Requirements](#requirements)\n- [Installation](#installation)\n- [Design](#design)\n- [Setup](#setup)\n- [Convention](#convention)\n- [API](#api)\n  - [SageAI Initialize](#sageai-initialize)\n  - [SageAI Methods](#sageai-methods)\n  - [Vector DB](#vector-db)\n- [Testing](#testing)\n  - [Unit Tests](#unit-tests)\n  - [Integration Tests](#integration-tests)\n  - [Output Equality](#output-equality)\n  - [CLI](#cli)\n- [Examples](#examples)\n- [Roadmap](#roadmap)\n- [Contributing](#contributing)\n\n## Key Features\n\n- Function organization through folder-centric functions.\n- Strong typing for functions using Pydantic.\n- Built-in Qdrant vector database with in-memory support for function storage and retrieval, with the option to\n  integrate your own.\n- Easily test each function with an associated `test.json` file, supporting both unit and integration tests.\n- Built with CI/CD in mind, ensuring synchronicity between your vector db and the functions directory across all\n  environments using the `index` method.\n- Lightweight implementation with only three dependencies:\n  - `openai`\n  - `pydantic`\n  - `qdrant-client`\n\n## Requirements\n\n```\npython >=3.9, <3.12\npydantic >=1.6, <=1.10.12\nopenai >=0.27.0\nqdrant-client >=1.4.0\n```\n\n## Installation\n\n```bash\n# pip\n$ pip install sageai\n\n# poetry\n$ poetry add sageai\n```\n\n## Design\n\n![Design](https://github.com/0xnenlabs/SageAI/assets/45445790/eb81d280-5b69-472a-b45a-4a9275fcf341)\n\nSageAI is built around the concept of a `functions` directory, which contains all of your functions. Each function is\ndefined in a Python file `function.py`, and is associated with an optional `test.json` file for testing.\n\nThe format of the `function.py` file must contain two things in order for SageAI to work:\n\n1. The function itself\n2. The `Function` object\n\nInput and output types may be defined using Pydantic models, and are automatically validated by SageAI. They can also be\ndefined outside the `function.py` file, and imported into the file.\n\nHere is a simplified example of how SageAI might handle a function that fetches the current weather for a given\nlocation.\n\n```python\n# functions/get_current_weather/function.py\nfrom enum import Enum\nfrom typing import Optional\n\nfrom pydantic import BaseModel, Field\n\nfrom sageai.types.function import Function\n\n\nclass UnitTypes(str, Enum):\n    CELSIUS = \"Celsius\"\n    FAHRENHEIT = \"Fahrenheit\"\n\n\nclass FunctionInput(BaseModel):\n    location: str = Field(\n        ..., description=\"The city, e.g. San Francisco\"\n    )\n    unit: Optional[UnitTypes] = Field(\n        UnitTypes.CELSIUS, description=\"The unit of temperature.\"\n    )\n\n\nclass FunctionOutput(BaseModel):\n    weather: str\n\n    def __eq__(self, other):\n        if not isinstance(other, FunctionOutput):\n            return False\n        return self.weather == other.weather\n\n\ndef get_current_weather(params: FunctionInput) -> FunctionOutput:\n    weather = (\n        f\"The weather in {params.location} is currently 22 degrees {params.unit.value}.\"\n    )\n    return FunctionOutput(weather=weather)\n\n\nfunction = Function(\n    function=get_current_weather,\n    description=\"Get the current weather in a given location.\",\n)\n```\n\nWe'll break down the above example into its components below.\n\n## Setup\n\nCreate a `functions` directory in the root directory, and add your functions as described in [Design](#design).\n\nThen initialize `SageAI`.\n\n```python\nfrom sageai import SageAI\n\nsage = SageAI(openai_key=\"\")\n```\n\nThen index the vector database.\n\n```python\nsage.index()\n```\n\nThat's it! You're now set up and ready to interact with SageAI through natural language queries. \ud83d\ude80\n\n```python\nmessage = \"What's the weather like in Toronto right now?\"\nresponse = sage.chat(\n    messages=[dict(role=\"user\", content=message)],\n    model=\"gpt-3.5-turbo-0613\",\n    top_n=5,\n)\n# response:\n# {\n#   'name': 'get_current_weather',\n#   'args': {'location': 'Toronto'},\n#   'result': {'weather': 'The weather in Toronto is currently 22 degrees Celsius.'}\n# }\n```\n\n## Convention\n\nSageAI follows a convention over configuration approach to make it easy to define functions.\n\nEnsure that your `function.py` file contains the following:\n\n1. A `function` object that is an instance of `Function`.\n2. A function that is the actual function that will be called by ChatGPT.\n3. The function **must** have typed input and output Pydantic models.\n4. Each field in the input model **must** have a description.\n\nMinimal example:\n\n```python\ndef my_function(params: PydanticInput) -> PydanticOutput:\n    return PydanticOutput(...)\n\n\nfunction = Function(\n    function=my_function,\n    description=\"My function description.\",\n)\n```\n\n## API\n\n### SageAI Initialize\n\nThe `SageAI` constructor accepts the following parameters:\n\n| Parameter               | Description                                                                 | Defaults                 |\n| ----------------------- | --------------------------------------------------------------------------- | ------------------------ |\n| **openai_key**          | The API key for OpenAI.                                                     | _Required_               |\n| **functions_directory** | Directory containing functions.                                             | `/functions`             |\n| **vectordb**            | An implementation of the `AbstractVectorDB` for vector database operations. | `DefaultVectorDBService` |\n| **log_level**           | Desired log level for the operations.                                       | `ERROR`                  |\n\n### SageAI Methods\n\n#### 1. `chat`\n\nInitiate a chat using OpenAI's API and the provided parameters.\n\n**Parameters**:\n\n| Parameter | Description                                                                                                         | Defaults   |\n| --------- | ------------------------------------------------------------------------------------------------------------------- | ---------- |\n| -         | Accepts the same parameters as OpenAI's [chat endpoint](https://platform.openai.com/docs/api-reference/chat/create) | -          |\n| **top_n** | The number of top functions to consider from the vector database.                                                   | _Required_ |\n\n**Returns**:\n\n```python\ndict(\n    name=\"function_name\",\n    args={\"arg1\": \"value1\", \"arg2\": \"value2\"},\n    result={\"out1\": \"value1\", \"out2\": \"value2\"},  # Optional\n    error=\"\",  # Optional\n)\n```\n\n> Either `result` or `error` will be present in the response, but not both.\n\n---\n\n#### 2. `get_top_n_functions`\n\nGet the top `n` functions from the vector database based on a query.\n\n**Parameters**:\n\n| Parameter | Description                        | Defaults   |\n| --------- | ---------------------------------- | ---------- |\n| **query** | The query to search against.       | _Required_ |\n| **top_n** | The number of functions to return. | _Required_ |\n\n**Returns**:\n\n- A dict of function names to `Function` definitions.\n\n---\n\n#### 3. `run_function`\n\nExecute a function based on its name and provided arguments.\n\n**Parameters**:\n\n| Parameter | Description                        | Defaults   |\n| --------- | ---------------------------------- | ---------- |\n| **name**  | Name of the function.              | _Required_ |\n| **args**  | Arguments to pass to the function. | _Required_ |\n\n**Returns**:\n\n- The function result as a dict.\n\n---\n\n#### 4. `call_openai`\n\nCalls the OpenAI API with the provided parameters.\n\n**Parameters**:\n\n| Parameter         | Description                                                                                                         | Defaults   |\n| ----------------- | ------------------------------------------------------------------------------------------------------------------- | ---------- |\n| **openai_args**   | Accepts the same parameters as OpenAI's [chat endpoint](https://platform.openai.com/docs/api-reference/chat/create) | _Required_ |\n| **top_functions** | List of dicts that is a representation of your functions.                                                           | _Required_ |\n\n**Returns**:\n\n- A tuple of the function name and the function args.\n\n---\n\n#### 5. `index`\n\nIndex the vector database based on the functions directory.\nThis method is useful to update the vectordb when new functions are added or existing ones are updated.\n\n---\n\nWant more control?\n\n> The `chat` function uses `get_top_n_functions`, `run_function`, and `call_openai` internally.\n> However, we also expose these methods incase you wish to use them directly to implement your own `chat` logic.\n\n---\n\n### Vector DB\n\nSageAI comes with a built-in in-memory vector database, Qdrant, which is used to store and retrieve functions.\n\nIf you wish to use your own vector database, you can implement the `AbstractVectorDB` class and pass it into the\n`SageAI` constructor.\n\nSee the [advanced example](/examples/advanced) for an example of how to integrate your own vector database.\n\n## Testing\n\nAs for the optional `test.json` file in each function, follow this structure:\n\n```json\n[\n  {\n    \"message\": \"What's the weather like in Toronto right now?\",\n    \"input\": {\n      \"location\": \"Toronto\",\n      \"unit\": \"Celsius\"\n    },\n    \"output\": {\n      \"weather\": \"The weather in Toronto is currently 22 degrees Celsius.\"\n    }\n  }\n]\n```\n\n- Each object in the array represents a test case.\n- The `message` field is the natural language message that will be sent\n  to ChatGPT, and the `input` field is the expected input that will be passed to the function.\n- The `output` field is the\n  expected output of the function.\n\nSageAI offers unit and integration tests.\n\n---\n\n### Unit Tests\n\n> Unit tests do not call the vector database nor ChatGPT, and **will not** cost you money.\n\n- Unit tests are used to ensure your functions directory is valid, and it tests the function in isolation.\n- It tests whether:\n  - the `functions` directory exists.\n  - each function has a `function.py` file.\n  - each `function.py` file has a `Function` object.\n  - and more!\n- It also tests whether the input and output types are valid, and whether the function returns the expected output based\n  on\n  the input alone by calling `func(test_case[\"input\"]) == test_case[\"output\"]`.\n\n---\n\n### Integration Tests\n\n> Integration tests will call the vector database and ChatGPT, and **will** cost you money.\n\n- Integration tests are used to test the function by calling ChatGPT and the vector database.\n- They test whether the vector database is able to retrieve the function, and whether ChatGPT can call the function\n  with the given input and return the expected output.\n\n> Because ChatGPT's responses can vary, integration tests may return different results each time.\n> It's important to use integration tests as a tool to ensure ChatGPT is able to call the right function with the right\n> input, and not as a definitive test to measure the test rate of your functions.\n\n---\n\n### Output Equality\n\nYou can customize how to determine equality between the expected and actual output by overriding the `__eq__`\nmethod in the output model.\n\n```python\nclass FunctionOutput(BaseModel):\n    weather: str\n    temperature: int\n\n    def __eq__(self, other):\n        if not isinstance(other, FunctionOutput):\n            return False\n        return self.weather == other.weather\n```\n\nIn the case above, we only care about the `weather` field, and not the `temperature` field. Therefore, we only compare\nthe `weather` field in the `__eq__` method.\n\nThis is especially useful when you are returning an object from a database, for example, and you only care to test\nagainst a subset of the fields (for example, the `id` field).\n\n---\n\n### CLI\n\n```bash\n# To run unit and integration tests for all functions:\npoetry run sageai-tests --apikey=openapikey --directory=path/to/functions\n\n# To run unit tests only for all functions:\npoetry run sageai-tests --apikey=openapikey --directory=path/to/functions --unit\n\n# To run integration tests only for all functions:\npoetry run sageai-tests --apikey=openapikey --directory=path/to/functions --integration\n\n# To run unit and integration tests for a specific function:\npoetry run sageai-tests --apikey=openapikey --directory=path/to/functions/get_current_weather\n```\n\n| Parameter         | Description                                                   | Defaults     |\n| ----------------- | ------------------------------------------------------------- | ------------ |\n| **--apikey**      | OpenAI API key.                                               | _Required_   |\n| **--directory**   | Directory of the functions or of the specific function to run | _/functions_ |\n| **--unit**        | Only run unit tests                                           | false        |\n| **--integration** | Only run integration tests                                    | false        |\n\n## Examples\n\n1. [Basic](/examples/basic) - Get started with a simple SageAI function.\n2. [Advanced](/examples/advanced) - Dive deeper with more intricate functionalities and use-cases.\n\n## Roadmap\n\n- [ ] Add tests and code coverage\n- [ ] Support multiple function calls\n- [ ] Support streaming\n- [ ] Support asyncio\n- [ ] Support Pydantic V2\n- [ ] Write Chainlit example\n- [ ] Write fullstack example\n\n## Contributing\n\nInterested in contributing to SageAI? Please see our [CONTRIBUTING.md](/CONTRIBUTING.md) for guidelines, coding\nstandards, and other details.\n",
    "bugtrack_url": null,
    "license": "MIT",
    "summary": "File-based functions for ChatGPT's function calling with Pydantic support",
    "version": "1.0.5",
    "project_urls": null,
    "split_keywords": [
        "python",
        "openai",
        "functions",
        "chatgpt",
        "gpt4",
        "genai",
        "function-calling"
    ],
    "urls": [
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "952304edcf76ac46e1ec3696e9a1b0dc5e12ffec0143d679f4ae26a802529e86",
                "md5": "4ceaa80280859f5e475a556147374c33",
                "sha256": "e12fe38c747a9e98ca2929ce23c69f7dbe43fb207a39796a0f6c8809c0ef9afb"
            },
            "downloads": -1,
            "filename": "sageai-1.0.5-py3-none-any.whl",
            "has_sig": false,
            "md5_digest": "4ceaa80280859f5e475a556147374c33",
            "packagetype": "bdist_wheel",
            "python_version": "py3",
            "requires_python": ">=3.9,<3.12",
            "size": 20219,
            "upload_time": "2023-11-15T16:24:58",
            "upload_time_iso_8601": "2023-11-15T16:24:58.422004Z",
            "url": "https://files.pythonhosted.org/packages/95/23/04edcf76ac46e1ec3696e9a1b0dc5e12ffec0143d679f4ae26a802529e86/sageai-1.0.5-py3-none-any.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "20649fa5fa6596cfbf46c5302056632a0df547e1f6e183dd692b8ff991e0e866",
                "md5": "42253d9b617a668f91169910bfd7b877",
                "sha256": "1947865b43076738d52896c32ea778c628973f064abb8fbdbe5a103dbfbc6039"
            },
            "downloads": -1,
            "filename": "sageai-1.0.5.tar.gz",
            "has_sig": false,
            "md5_digest": "42253d9b617a668f91169910bfd7b877",
            "packagetype": "sdist",
            "python_version": "source",
            "requires_python": ">=3.9,<3.12",
            "size": 19184,
            "upload_time": "2023-11-15T16:24:59",
            "upload_time_iso_8601": "2023-11-15T16:24:59.780807Z",
            "url": "https://files.pythonhosted.org/packages/20/64/9fa5fa6596cfbf46c5302056632a0df547e1f6e183dd692b8ff991e0e866/sageai-1.0.5.tar.gz",
            "yanked": false,
            "yanked_reason": null
        }
    ],
    "upload_time": "2023-11-15 16:24:59",
    "github": false,
    "gitlab": false,
    "bitbucket": false,
    "codeberg": false,
    "lcname": "sageai"
}
        
Elapsed time: 3.01089s