sunholo 0.107.0__tar.gz → 0.109.1__tar.gz
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.
- {sunholo-0.107.0 → sunholo-0.109.1}/PKG-INFO +2 -2
- {sunholo-0.107.0 → sunholo-0.109.1}/setup.py +1 -1
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/alloydb.py +6 -4
- sunholo-0.109.1/sunholo/genai/__init__.py +4 -0
- sunholo-0.109.1/sunholo/genai/file_handling.py +186 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/senses/stream_voice.py +39 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo.egg-info/PKG-INFO +2 -2
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo.egg-info/SOURCES.txt +1 -0
- sunholo-0.107.0/sunholo/genai/__init__.py +0 -3
- {sunholo-0.107.0 → sunholo-0.109.1}/LICENSE.txt +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/MANIFEST.in +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/README.md +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/setup.cfg +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/chat_history.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/dispatch_to_qa.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/fastapi/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/fastapi/base.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/fastapi/qna_routes.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/flask/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/flask/base.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/flask/qna_routes.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/flask/vac_routes.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/langserve.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/pubsub.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/route.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/special_commands.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/agents/swagger.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/archive/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/archive/archive.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/auth/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/auth/gcloud.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/auth/refresh.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/auth/run.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/azure/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/azure/auth.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/azure/blobs.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/azure/event_grid.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/bots/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/bots/discord.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/bots/github_webhook.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/bots/webapp.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/azure.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/doc_handling.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/encode_metadata.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/images.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/loaders.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/message_data.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/pdfs.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/process_chunker_data.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/publish.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/pubsub.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/chunker/splitter.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/chat_vac.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/cli.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/cli_init.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/configs.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/deploy.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/embedder.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/merge_texts.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/run_proxy.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/sun_rich.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/swagger.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/cli/vertex.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/components/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/components/llm.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/components/retriever.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/components/vectorstore.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/custom_logging.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/alloydb_client.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/database.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/lancedb.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/sql/sb/create_function.sql +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/sql/sb/create_function_time.sql +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/sql/sb/create_table.sql +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/sql/sb/delete_source_row.sql +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/sql/sb/return_sources.sql +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/sql/sb/setup.sql +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/static_dbs.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/database/uuid.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/discovery_engine/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/discovery_engine/chunker_handler.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/discovery_engine/create_new.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/discovery_engine/discovery_engine_client.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/discovery_engine/get_ai_search_chunks.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/embedder/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/embedder/embed_chunk.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/excel/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/excel/plugin.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/gcs/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/gcs/add_file.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/gcs/download_folder.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/gcs/download_url.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/gcs/extract_and_sign.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/gcs/metadata.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/genai/images.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/genai/init.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/genai/process_funcs_cls.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/genai/safety.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/invoke/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/invoke/async_class.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/invoke/direct_vac_func.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/invoke/invoke_vac_utils.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/langfuse/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/langfuse/callback.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/langfuse/evals.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/langfuse/prompts.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/llamaindex/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/llamaindex/get_files.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/llamaindex/import_files.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/llamaindex/llamaindex_class.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/llamaindex/user_history.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/lookup/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/lookup/model_lookup.yaml +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/patches/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/patches/langchain/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/patches/langchain/lancedb.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/patches/langchain/vertexai.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/pubsub/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/pubsub/process_pubsub.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/pubsub/pubsub_manager.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/qna/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/qna/parsers.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/qna/retry.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/senses/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/streaming/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/streaming/content_buffer.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/streaming/langserve.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/streaming/stream_lookup.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/streaming/streaming.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/summarise/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/summarise/summarise.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/terraform/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/terraform/tfvars_editor.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/tools/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/tools/web_browser.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/api_key.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/big_context.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/config.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/config_class.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/config_schema.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/gcp.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/gcp_project.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/mime.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/parsers.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/timedelta.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/user_ids.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/utils/version.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/__init__.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/extensions_call.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/extensions_class.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/genai_functions.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/init.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/memory_tools.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/safety.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo/vertex/type_dict_to_json.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo.egg-info/dependency_links.txt +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo.egg-info/entry_points.txt +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo.egg-info/requires.txt +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/sunholo.egg-info/top_level.txt +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/tests/test_async.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/tests/test_chat_history.py +0 -0
- {sunholo-0.107.0 → sunholo-0.109.1}/tests/test_config.py +0 -0
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: sunholo
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.109.1
|
|
4
4
|
Summary: Large Language Model DevOps - a package to help deploy LLMs to the Cloud.
|
|
5
5
|
Home-page: https://github.com/sunholo-data/sunholo-py
|
|
6
|
-
Download-URL: https://github.com/sunholo-data/sunholo-py/archive/refs/tags/v0.
|
|
6
|
+
Download-URL: https://github.com/sunholo-data/sunholo-py/archive/refs/tags/v0.109.1.tar.gz
|
|
7
7
|
Author: Holosun ApS
|
|
8
8
|
Author-email: multivac@sunholo.com
|
|
9
9
|
License: Apache License, Version 2.0
|
|
@@ -275,17 +275,19 @@ def _list_sources_from_docstore(sources, vector_name, search_type="OR"):
|
|
|
275
275
|
if sources:
|
|
276
276
|
conditions = and_or_ilike(sources, search_type=search_type)
|
|
277
277
|
query = f"""
|
|
278
|
-
SELECT
|
|
278
|
+
SELECT source AS objectId
|
|
279
279
|
FROM {table_name}
|
|
280
280
|
WHERE {conditions}
|
|
281
|
-
|
|
281
|
+
GROUP BY source
|
|
282
|
+
ORDER BY source ASC
|
|
282
283
|
LIMIT 500;
|
|
283
284
|
"""
|
|
284
285
|
else:
|
|
285
286
|
query = f"""
|
|
286
|
-
SELECT
|
|
287
|
+
SELECT source AS objectId
|
|
287
288
|
FROM {table_name}
|
|
288
|
-
|
|
289
|
+
GROUP BY source
|
|
290
|
+
ORDER BY source ASC
|
|
289
291
|
LIMIT 500;
|
|
290
292
|
"""
|
|
291
293
|
|
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
from ..custom_logging import log
|
|
2
|
+
from ..gcs import get_bytes_from_gcs
|
|
3
|
+
|
|
4
|
+
import mimetypes
|
|
5
|
+
import asyncio
|
|
6
|
+
import tempfile
|
|
7
|
+
import re
|
|
8
|
+
import traceback
|
|
9
|
+
try:
|
|
10
|
+
import google.generativeai as genai
|
|
11
|
+
from google.generativeai.types import file_types
|
|
12
|
+
except ImportError:
|
|
13
|
+
genai = None
|
|
14
|
+
file_types = None
|
|
15
|
+
|
|
16
|
+
DOCUMENT_MIMES = [
|
|
17
|
+
'application/pdf',
|
|
18
|
+
'application/x-javascript',
|
|
19
|
+
'text/javascript',
|
|
20
|
+
'application/x-python',
|
|
21
|
+
'text/x-python',
|
|
22
|
+
'text/plain',
|
|
23
|
+
'text/html',
|
|
24
|
+
'text/css',
|
|
25
|
+
'text/md',
|
|
26
|
+
'text/csv',
|
|
27
|
+
'text/xml',
|
|
28
|
+
'text/rtf'
|
|
29
|
+
]
|
|
30
|
+
|
|
31
|
+
IMAGE_MIMES = [
|
|
32
|
+
'image/png',
|
|
33
|
+
'image/jpeg',
|
|
34
|
+
'image/webp',
|
|
35
|
+
'image/heic',
|
|
36
|
+
'image/heif',
|
|
37
|
+
]
|
|
38
|
+
|
|
39
|
+
VIDEO_MIMES = [
|
|
40
|
+
'video/mp4',
|
|
41
|
+
'video/mpeg',
|
|
42
|
+
'video/mov',
|
|
43
|
+
'video/avi',
|
|
44
|
+
'video/x-flv',
|
|
45
|
+
'video/mpg',
|
|
46
|
+
'video/webm',
|
|
47
|
+
'video/wmv',
|
|
48
|
+
'video/3gpp'
|
|
49
|
+
]
|
|
50
|
+
|
|
51
|
+
AUDIO_MIMES = [
|
|
52
|
+
'audio/wav',
|
|
53
|
+
'audio/mp3',
|
|
54
|
+
'audio/aiff',
|
|
55
|
+
'audio/aac',
|
|
56
|
+
'audio/ogg',
|
|
57
|
+
'audio/flac',
|
|
58
|
+
]
|
|
59
|
+
|
|
60
|
+
ALLOWED_MIME_TYPES = set(AUDIO_MIMES + VIDEO_MIMES + IMAGE_MIMES + DOCUMENT_MIMES)
|
|
61
|
+
|
|
62
|
+
# 'documents':
|
|
63
|
+
# [
|
|
64
|
+
# {'storagePath': 'users/UQcKi4u7s...dsd.png',
|
|
65
|
+
# 'url': 'https://firebasestorage.googleapis.com/v0/b/multi...',
|
|
66
|
+
# 'contentType': 'image/png',
|
|
67
|
+
# 'type': 'image',
|
|
68
|
+
# 'name': 'multivac-data-architecture.png'},
|
|
69
|
+
# {'storagePath': 'users/UQc...3dc59e1.jpg',
|
|
70
|
+
# 'type': 'image',
|
|
71
|
+
# 'name': 'holosun-circle.jpg',
|
|
72
|
+
# 'url': 'https://firebasestorage.googleapis.com/v0/b/multiv...',
|
|
73
|
+
# 'contentType': 'image/jpeg'}
|
|
74
|
+
# ]
|
|
75
|
+
async def construct_file_content(gs_list, bucket:str):
|
|
76
|
+
"""
|
|
77
|
+
Args:
|
|
78
|
+
- gs_list: a list of dicts representing files in a bucket
|
|
79
|
+
- contentType: The content type of the file on GCS
|
|
80
|
+
- storagePath: The path in the bucket
|
|
81
|
+
- bucket: The bucket the files are in
|
|
82
|
+
|
|
83
|
+
"""
|
|
84
|
+
|
|
85
|
+
file_list = []
|
|
86
|
+
for element in gs_list:
|
|
87
|
+
|
|
88
|
+
the_mime_type = element.get('contentType')
|
|
89
|
+
if the_mime_type is None:
|
|
90
|
+
continue
|
|
91
|
+
if element.get('storagePath') is None:
|
|
92
|
+
continue
|
|
93
|
+
if the_mime_type in ALLOWED_MIME_TYPES:
|
|
94
|
+
file_list.append(element)
|
|
95
|
+
|
|
96
|
+
if not file_list:
|
|
97
|
+
return {"role": "user", "parts": [{"text": "No eligible contentTypes were found"}]}
|
|
98
|
+
|
|
99
|
+
content = []
|
|
100
|
+
|
|
101
|
+
# Loop through the valid files and process them
|
|
102
|
+
tasks = []
|
|
103
|
+
for file_info in file_list:
|
|
104
|
+
img_url = f"gs://{bucket}/{file_info['storagePath']}"
|
|
105
|
+
mime_type = file_info['contentType']
|
|
106
|
+
# Append the async download task to the task list
|
|
107
|
+
tasks.append(download_gcs_upload_genai(img_url, mime_type))
|
|
108
|
+
|
|
109
|
+
# Run all tasks in parallel
|
|
110
|
+
content = await asyncio.gather(*tasks)
|
|
111
|
+
|
|
112
|
+
return content
|
|
113
|
+
|
|
114
|
+
# Helper function to handle each file download with error handling
|
|
115
|
+
async def download_file_with_error_handling(img_url, mime_type):
|
|
116
|
+
try:
|
|
117
|
+
return await download_gcs_upload_genai(img_url, mime_type)
|
|
118
|
+
except Exception as err:
|
|
119
|
+
msg= f"Error processing file from {img_url}: {str(err)}"
|
|
120
|
+
log.error(msg)
|
|
121
|
+
return {"role": "user", "parts": [{"text": msg}]}
|
|
122
|
+
|
|
123
|
+
async def download_gcs_upload_genai(img_url, mime_type, retries=3, delay=2):
|
|
124
|
+
import aiofiles
|
|
125
|
+
"""
|
|
126
|
+
Downloads and uploads a file with retries in case of failure.
|
|
127
|
+
|
|
128
|
+
Args:
|
|
129
|
+
- img_url: str The URL of the file to download.
|
|
130
|
+
- mime_type: str The MIME type of the file.
|
|
131
|
+
- retries: int Number of retry attempts before failing.
|
|
132
|
+
- delay: int Initial delay between retries, exponentially increasing.
|
|
133
|
+
|
|
134
|
+
Returns:
|
|
135
|
+
- downloaded_content: The result of the file upload if successful.
|
|
136
|
+
"""
|
|
137
|
+
for attempt in range(retries):
|
|
138
|
+
try:
|
|
139
|
+
log.info(f"Upload {attempt} for {img_url=}")
|
|
140
|
+
# Download the file bytes asynchronously
|
|
141
|
+
file_bytes = await asyncio.to_thread(get_bytes_from_gcs, img_url)
|
|
142
|
+
if not file_bytes:
|
|
143
|
+
msg = f"Failed to download file from {img_url}: got None"
|
|
144
|
+
log.warning(msg)
|
|
145
|
+
return {"role": "user", "parts": [{"text": msg}]}
|
|
146
|
+
|
|
147
|
+
# Log the size of the file bytes
|
|
148
|
+
file_size = len(file_bytes)
|
|
149
|
+
log.info(f"Downloaded file size for {img_url}: {file_size} bytes")
|
|
150
|
+
|
|
151
|
+
if file_size > 19434343:
|
|
152
|
+
log.warning(f"File size for {img_url}: {file_size} is too big.")
|
|
153
|
+
msg = f"The file for {img_url} is too large ({file_size} bytes) to be used directly. Use RAG instead."
|
|
154
|
+
return {"role": "user", "parts": [{"text": msg}]}
|
|
155
|
+
|
|
156
|
+
extension = mimetypes.guess_extension(mime_type)
|
|
157
|
+
|
|
158
|
+
# Use aiofiles for asynchronous file operations
|
|
159
|
+
temp_file = tempfile.NamedTemporaryFile(delete=False, suffix=extension)
|
|
160
|
+
downloaded_file = temp_file.name
|
|
161
|
+
|
|
162
|
+
sanitized_file = re.sub(r'[^\w\-.]', '_', downloaded_file)
|
|
163
|
+
|
|
164
|
+
log.info(f"Writing file {sanitized_file}")
|
|
165
|
+
async with aiofiles.open(sanitized_file, 'wb') as f:
|
|
166
|
+
await f.write(file_bytes)
|
|
167
|
+
|
|
168
|
+
# Upload the file and get its content reference
|
|
169
|
+
try:
|
|
170
|
+
downloaded_content: file_types.File = await asyncio.to_thread(genai.upload_file, sanitized_file )
|
|
171
|
+
return {"role": "user", "parts": [{"file_data": downloaded_content}]}
|
|
172
|
+
except Exception as err:
|
|
173
|
+
msg = f"Could not upload {sanitized_file} to genai.upload_file: {str(err)} {traceback.format_exc()}"
|
|
174
|
+
log.error(msg)
|
|
175
|
+
return {"role": "user", "parts": [{"text": msg}]}
|
|
176
|
+
|
|
177
|
+
except Exception as err:
|
|
178
|
+
log.error(f"Error processing file {img_url} on attempt {attempt + 1}/{retries}: {str(err)}")
|
|
179
|
+
|
|
180
|
+
if attempt < retries - 1:
|
|
181
|
+
log.info(f"Retrying in {delay} seconds...")
|
|
182
|
+
await asyncio.sleep(delay)
|
|
183
|
+
delay *= 2 # Exponential backoff
|
|
184
|
+
else:
|
|
185
|
+
raise err # Raise the error after max retries
|
|
186
|
+
|
|
@@ -23,6 +23,8 @@ import queue
|
|
|
23
23
|
import threading
|
|
24
24
|
import time
|
|
25
25
|
from concurrent.futures import ThreadPoolExecutor
|
|
26
|
+
import io
|
|
27
|
+
import wave
|
|
26
28
|
|
|
27
29
|
import argparse
|
|
28
30
|
import json
|
|
@@ -131,6 +133,43 @@ class StreamingTTS:
|
|
|
131
133
|
# Convert audio bytes to numpy array for playback
|
|
132
134
|
audio_np = np.frombuffer(response.audio_content, dtype=np.int16)
|
|
133
135
|
return audio_np
|
|
136
|
+
|
|
137
|
+
def generate_audio_stream(self, text):
|
|
138
|
+
"""
|
|
139
|
+
Generate a stream of audio data from a text chunk.
|
|
140
|
+
Returns audio in WAV format for streaming.
|
|
141
|
+
|
|
142
|
+
Args:
|
|
143
|
+
text (str): Text to convert to speech
|
|
144
|
+
|
|
145
|
+
Yields:
|
|
146
|
+
bytes: WAV-formatted audio data
|
|
147
|
+
"""
|
|
148
|
+
try:
|
|
149
|
+
# Convert text to audio using existing method
|
|
150
|
+
audio_chunk = self.text_to_audio(text)
|
|
151
|
+
|
|
152
|
+
# Process audio chunk with fading
|
|
153
|
+
processed_chunk = self._apply_fade(
|
|
154
|
+
audio_chunk,
|
|
155
|
+
fade_duration=self.file_fade_duration,
|
|
156
|
+
fade_in=True,
|
|
157
|
+
fade_out=True
|
|
158
|
+
)
|
|
159
|
+
|
|
160
|
+
# Convert to WAV format
|
|
161
|
+
wav_buffer = io.BytesIO()
|
|
162
|
+
with wave.open(wav_buffer, 'wb') as wav_file:
|
|
163
|
+
wav_file.setnchannels(1)
|
|
164
|
+
wav_file.setsampwidth(2)
|
|
165
|
+
wav_file.setframerate(self.sample_rate)
|
|
166
|
+
wav_file.writeframes(processed_chunk.tobytes())
|
|
167
|
+
|
|
168
|
+
yield wav_buffer.getvalue()
|
|
169
|
+
|
|
170
|
+
except Exception as e:
|
|
171
|
+
log.error(f"Error generating audio stream: {e}")
|
|
172
|
+
yield b''
|
|
134
173
|
|
|
135
174
|
def _initialize_audio_device(self):
|
|
136
175
|
"""Initialize audio device with proper settings."""
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: sunholo
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.109.1
|
|
4
4
|
Summary: Large Language Model DevOps - a package to help deploy LLMs to the Cloud.
|
|
5
5
|
Home-page: https://github.com/sunholo-data/sunholo-py
|
|
6
|
-
Download-URL: https://github.com/sunholo-data/sunholo-py/archive/refs/tags/v0.
|
|
6
|
+
Download-URL: https://github.com/sunholo-data/sunholo-py/archive/refs/tags/v0.109.1.tar.gz
|
|
7
7
|
Author: Holosun ApS
|
|
8
8
|
Author-email: multivac@sunholo.com
|
|
9
9
|
License: Apache License, Version 2.0
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|