Skip to content

Commit

Permalink
Add new files and modules
Browse files Browse the repository at this point in the history
  • Loading branch information
ReinderVosDeWael committed Dec 8, 2023
1 parent 09554a3 commit 9a0b728
Show file tree
Hide file tree
Showing 20 changed files with 1,435 additions and 157 deletions.
53 changes: 13 additions & 40 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,59 +1,32 @@
# CMI-DAIR Template Python Repository

This is a template repository. Below is a checklist of things you should do to use it:

- [x] Run `setup_template.py` to set up the repository.
- [ ] Rewrite this `README` file.
- [ ] Install the `pre-commit` hooks.
- [x] Update the `LICENSE` file to your desired license and set the year.
- [ ] Update the supported versions in `SECURITY.md` or, if not relevant, delete this file.
- [ ] Remove the placeholder src and test files, these are there merely to show how the CI works.
- [ ] Grant third-party app permissions (e.g. Codecov) [here](https://github.com/organizations/cmi-dair/settings/installations), if necessary.
- [ ] Either generate a `CODECOV_TOKEN` secret [here](https://github.com/cmi-dair/flowdump/blob/main/.github/workflows/python_tests.yaml) (if its a private repository) or remove the line `token: ${{ secrets.CODECOV_TOKEN }}`
- [ ] API docs website: After the first successful build, go to the `Settings` tab of your repository, scroll down to the `GitHub Pages` section, and select `gh-pages` as the source. This will generate a link to your API docs.
- [ ] Update stability badge in `README.md` to reflect the current state of the project. A list of stability badges to copy can be found [here](https://github.com/orangemug/stability-badges). The [node documentation](https://nodejs.org/docs/latest-v20.x/api/documentation.html#documentation_stability_index) can be used as a reference for the stability levels.

# Project name
# CLI-OAI

[![Build](https://github.com/cmi-dair/cli-oai/actions/workflows/test.yaml/badge.svg?branch=main)](https://github.com/cmi-dair/cli-oai/actions/workflows/test.yaml?query=branch%3Amain)
[![codecov](https://codecov.io/gh/cmi-dair/cli-oai/branch/main/graph/badge.svg?token=22HWWFWPW5)](https://codecov.io/gh/cmi-dair/cli-oai)
[![Ruff](https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json)](https://github.com/astral-sh/ruff)
![stability-wip](https://img.shields.io/badge/stability-work_in_progress-lightgrey.svg)
[![MIT License](https://img.shields.io/badge/license-MIT-blue.svg)](https://github.com/cmi-dair/cli-oai/blob/main/LICENSE)
[![MIT License](https://img.shields.io/badge/license-LGPL_2.1-blue.svg)](https://github.com/cmi-dair/cli-oai/blob/main/LICENSE)
[![pages](https://img.shields.io/badge/api-docs-blue)](https://cmi-dair.github.io/cli-oai)

What problem does this tool solve?
CLI-OAI is a Python command-line interface for interacting with the OpenAI API.

## Features
## Usage

- A few
- Cool
- Things
Before running oai, make sure the environment variable OPENAI_API_KEY is set to
your API key. To use the CLI, run `oai --help` in your terminal. See the `--help`
function of the subcommands for more information on each command.

## Installation

Install this package via :

```sh
pip install oai
```

Or get the newest development version via:
Get the newest development version via:

```sh
pip install git+https://github.com/cmi-dair/cli-oai
poetry add git+https://github.com/cmi-dair/cli-oai
```

## Quick start

Short tutorial, maybe with a
## Contributing

```Python
import oai

oai.short_example()
```
Please see the [contributing guidelines](CONTRIBUTING.md) for guidelines on contributing to this project.

## Links or References
## License

- [https://www.wikipedia.de](https://www.wikipedia.de)
This project is licensed under the terms of the [L-GPLv2.1 license](LICENSE).
20 changes: 0 additions & 20 deletions SECURITY.md

This file was deleted.

551 changes: 539 additions & 12 deletions poetry.lock

Large diffs are not rendered by default.

80 changes: 50 additions & 30 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,20 @@ packages = [{include = "oai", from = "src"}]

[tool.poetry.dependencies]
python = "^3.11"
pydantic-settings = "^2.1.0"
pydantic = "^2.5.2"
ffmpeg-python = "^0.2.0"
openai = "^1.3.7"
requests = "^2.31.0"

[tool.poetry.group.dev.dependencies]
pytest = "^7.4.3"
mypy = "^1.7.1"
pre-commit = "^3.5.0"
pytest-cov = "^4.1.0"
ruff = "^0.1.7"
pytest-mock = "^3.12.0"
pytest-asyncio = "^0.23.2"

[tool.poetry.group.docs.dependencies]
pdoc = "^14.1.0"
Expand All @@ -28,43 +35,48 @@ pythonpath = [
"src"
]

[tool.poetry.scripts]
oai = 'oai.__main__:main'

[tool.mypy]
ignore_missing_imports = true

[tool.ruff]
exclude = [
".bzr",
".direnv",
".eggs",
".git",
".git-rewrite",
".hg",
".mypy_cache",
".nox",
".pants.d",
".pytype",
".ruff_cache",
".svn",
".tox",
".venv",
"__pypackages__",
"_build",
"buck-out",
"build",
"dist",
"node_modules",
"venv"
".bzr",
".direnv",
".eggs",
".git",
".git-rewrite",
".hg",
".mypy_cache",
".nox",
".pants.d",
".pytype",
".ruff_cache",
".svn",
".tox",
".venv",
"__pypackages__",
"_build",
"buck-out",
"build",
"dist",
"node_modules",
"venv",
]
line-length = 88
indent-width = 4
src = ["src"]
src=["src"]

target-version = "py311"

[tool.ruff.lint]
select = ["ANN", "D", "E", "F", "I"]
select = ["ALL"]
ignore = [
"ANN101", # self should not be annotated.
"ANN102" # cls should not be annotated.
"ANN101", # Self should never be type annotated.
"ANN102", # cls should never be type annotated.
"B008", # Allow function call in arguments; this is common in FastAPI.
]
fixable = ["ALL"]
unfixable = []
Expand All @@ -80,8 +92,16 @@ line-ending = "auto"
convention = "google"

[tool.ruff.per-file-ignores]
"tests/**/*.py" = []

[build-system]
requires = ["poetry-core>=1.2.0"]
build-backend = "poetry.core.masonry.api"
"tests/**/*.py" = [
"S101", # Allow assets
"ARG", # Unused arguments are common in tests (fixtures).
"FBT", #Allow positional booleans
"SLF001", # Allow private member access.
"INP001", # No need for namespace packages in tests.
]
"src/**/models.py" = [
"A003", # Allow id as a field name.
]
"src/**/schemas.py" = [
"A003", # Allow id as a field name.
]
13 changes: 13 additions & 0 deletions src/oai/__main__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
"""Entry point of the OAI package."""
import asyncio

from oai.cli import parser


def main() -> None:
"""Entry point for the CLI."""
asyncio.run(parser.parse_args())


if __name__ == "__main__":
main()
23 changes: 0 additions & 23 deletions src/oai/algorithms.py

This file was deleted.

1 change: 1 addition & 0 deletions src/oai/cli/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
"""Modules for the Command Line Interface."""
101 changes: 101 additions & 0 deletions src/oai/cli/commands.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,101 @@
"""Contains the core business logic of the OpenAI CLI."""
import asyncio
import logging
import pathlib
import tempfile

import ffmpeg

from oai import openai_api
from oai.cli import utils
from oai.core import config

settings = config.get_settings()
logger = logging.getLogger(settings.LOGGER_NAME)
MAX_FILE_SIZE = 24_500_000 # Max size is 25MB, but we leave some room for error.


async def speech_to_text(
filename: pathlib.Path,
model: str,
*,
clip: bool = False,
) -> str:
"""Transcribes audio files with OpenAI's TTS models.
Args:
filename: The file to transcribe. Can be any format that ffmpeg supports.
model: The transcription model to use.
voice: The voice to use.
clip: Whether to clip the file if it is too large, defaults to False.
"""
with tempfile.TemporaryDirectory() as temp_dir:
temp_file = pathlib.Path(temp_dir) / "temp.mp3"
ffmpeg.input(filename).output(str(temp_file)).overwrite_output().run()

if clip:
files = utils.clip_audio(temp_file, temp_dir, MAX_FILE_SIZE)
else:
files = [temp_file]

stt = openai_api.SpeechToText()
transcription_promises = [stt.run(filename, model=model) for filename in files]
transcriptions = await asyncio.gather(*transcription_promises)

return " ".join(transcriptions)


async def text_to_speech(
text: str,
output_file: str,
model: str,
voice: str,
) -> bytes:
"""Converts text to speech with OpenAI's TTS models.
Args:
text: The text to convert to speech.
output_file: The name of the output file.
model: The model to use.
voice: The voice to use.
"""
tts = openai_api.TextToSpeech()
return await tts.run(text, output_file, model=model, voice=voice)


async def image_generation( # noqa: PLR0913
prompt: str,
output_base_name: str,
model: str,
width: int,
height: int,
quality: str,
n: int,
) -> None:
"""Generates an image from text with OpenAI's Image Generation models.
Args:
prompt: The text to generate an image from.
output_base_name: The base name of the output file.
model: The model to use.
width: The width of the generated image. Defaults to 1024.
height: The height of the generated image. Defaults to 1024.
quality: The quality of the generated image. Defaults to "standard".
n: The number of images to generate. Defaults to 1.
Returns:
bytes: The generated image as bytes.
"""
image_generation = openai_api.ImageGeneration()
urls = await image_generation.run(
prompt,
model=model,
width=width,
height=height,
quality=quality,
n=n,
)

for index, url in enumerate(urls):
file = pathlib.Path(f"{output_base_name}_{index}.png")
utils.download_file(file, url)
Loading

0 comments on commit 9a0b728

Please sign in to comment.